I've translated an [implementation of strlen in x86 assembly][1] to C and added alignment checking:

```
#include <strings.h>
#include <string.h>
#include <stdint.h>

#define NOT_HIGH_MASK 0x080808080
#define HIGH_MASK 0x7f7f7f7f
#define LOW_MASK 0x01010101
#define mul4(x) ((x) << 2)
#define div8(x) ((x) >> 3)

size_t strlen(const char *str)
{
    const char *cptr = str;
    uint32_t i, *s;
    size_t ctr = 0;

    /* Satisfy alignment requirements */
    while((uintptr_t)cptr & (sizeof(uint32_t)-1))
    {
        if(!*cptr)
            return cptr - str;
        cptr++;
    }

    s = (uint32_t *)cptr;

    do {
        i = s[ctr];
        /* Mask off high bit */
        i &= HIGH_MASK;
        /* subtract 0x01 from each byte,
           giving a set high bit if it
           was zero */
        i -= LOW_MASK;
        ctr++;
            /* Test for the set high bit
               and if it is found exit */
    } while(!(i &= NOT_HIGH_MASK));

    /* Find the first high bit set and
       create the corresponding byte index */
    i = div8(ffs(i));
    /* Remove the counter increment from the
       loop and multiply it by 4 to find the
       rest of the byte index */
    ctr = mul4(ctr - 1);

    /* Return the combined byte index with 1
       removed so it doesn't include the null
       terminator itself */
    return i + ctr - 1;
}
```

I'm looking for general critique, but I'd also like additional information in these areas:

* Portability. Is this portable? Will it work on all common platforms (x86, arm, etc.) and possibly some uncommon ones?

* Comments. The comments I've put here seem to already document the code well enough, but is there any additional information I could add?

* Hidden Bugs. This definitely works (and has a noticeable improvement in speed), but are there any hidden bugs relating to alignment requirements or otherwise (such as extended ASCII)? For context, this is part of a standard C/POSIX library implementation.

I might note that I'm relying on my header to use the builtin version of `ffs`. This may be an issue on non-GNU compilers.

  [1]: https://codereview.stackexchange.com/questions/210689/strlen-and-strcmp-implementation-in-x86-fasm-assembly/213558#213558