LLVMFuzzerTestOneInput:
   30|    640|int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
   31|    640|    if (size < sizeof(inputArgs)) {
  ------------------
  |  Branch (31:9): [True: 8, False: 632]
  ------------------
   32|      8|        return 0;
   33|      8|    }
   34|    632|    const inputArgs *args = (const inputArgs *)data;
   35|       |
   36|    632|    H3_EXPORT(getResolution)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   37|    632|    H3_EXPORT(getBaseCellNumber)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   38|    632|    H3_EXPORT(isValidIndex)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   39|    632|    H3_EXPORT(isValidCell)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   40|    632|    H3_EXPORT(isPentagon)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   41|    632|    H3_EXPORT(isResClassIII)(args->index);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   42|       |
   43|    632|    int faceCount;
   44|    632|    H3Error err = H3_EXPORT(maxFaceCount)(args->index, &faceCount);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   45|    632|    if (!err && faceCount > 0) {
  ------------------
  |  Branch (45:9): [True: 632, False: 0]
  |  Branch (45:17): [True: 632, False: 0]
  ------------------
   46|    632|        int *out = calloc(faceCount, sizeof(int));
   47|    632|        H3_EXPORT(getIcosahedronFaces)(args->index, out);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   48|    632|        free(out);
   49|    632|    }
   50|       |
   51|    632|    int digitOut;
   52|    632|    H3_EXPORT(getIndexDigit)(args->index, args->res, &digitOut);
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   53|       |
   54|    632|    return 0;
   55|    640|}

h3Index.c:_rotate60ccw:
  656|  1.67k|static inline Direction _rotate60ccw(Direction digit) {
  657|  1.67k|    switch (digit) {
  658|    311|        case K_AXES_DIGIT:
  ------------------
  |  Branch (658:9): [True: 311, False: 1.36k]
  ------------------
  659|    311|            return IK_AXES_DIGIT;
  660|    273|        case IK_AXES_DIGIT:
  ------------------
  |  Branch (660:9): [True: 273, False: 1.40k]
  ------------------
  661|    273|            return I_AXES_DIGIT;
  662|    251|        case I_AXES_DIGIT:
  ------------------
  |  Branch (662:9): [True: 251, False: 1.42k]
  ------------------
  663|    251|            return IJ_AXES_DIGIT;
  664|    253|        case IJ_AXES_DIGIT:
  ------------------
  |  Branch (664:9): [True: 253, False: 1.42k]
  ------------------
  665|    253|            return J_AXES_DIGIT;
  666|    253|        case J_AXES_DIGIT:
  ------------------
  |  Branch (666:9): [True: 253, False: 1.42k]
  ------------------
  667|    253|            return JK_AXES_DIGIT;
  668|    280|        case JK_AXES_DIGIT:
  ------------------
  |  Branch (668:9): [True: 280, False: 1.39k]
  ------------------
  669|    280|            return K_AXES_DIGIT;
  670|     58|        default:
  ------------------
  |  Branch (670:9): [True: 58, False: 1.62k]
  ------------------
  671|     58|            return digit;
  672|  1.67k|    }
  673|  1.67k|}
h3Index.c:_rotate60cw:
  680|  2.17k|static inline Direction _rotate60cw(Direction digit) {
  681|  2.17k|    switch (digit) {
  682|    265|        case K_AXES_DIGIT:
  ------------------
  |  Branch (682:9): [True: 265, False: 1.91k]
  ------------------
  683|    265|            return JK_AXES_DIGIT;
  684|    303|        case JK_AXES_DIGIT:
  ------------------
  |  Branch (684:9): [True: 303, False: 1.87k]
  ------------------
  685|    303|            return J_AXES_DIGIT;
  686|    200|        case J_AXES_DIGIT:
  ------------------
  |  Branch (686:9): [True: 200, False: 1.97k]
  ------------------
  687|    200|            return IJ_AXES_DIGIT;
  688|    219|        case IJ_AXES_DIGIT:
  ------------------
  |  Branch (688:9): [True: 219, False: 1.95k]
  ------------------
  689|    219|            return I_AXES_DIGIT;
  690|    287|        case I_AXES_DIGIT:
  ------------------
  |  Branch (690:9): [True: 287, False: 1.89k]
  ------------------
  691|    287|            return IK_AXES_DIGIT;
  692|    352|        case IK_AXES_DIGIT:
  ------------------
  |  Branch (692:9): [True: 352, False: 1.82k]
  ------------------
  693|    352|            return K_AXES_DIGIT;
  694|    552|        default:
  ------------------
  |  Branch (694:9): [True: 552, False: 1.62k]
  ------------------
  695|    552|            return digit;
  696|  2.17k|    }
  697|  2.17k|}
h3Index.c:_downAp7:
  512|  8.47k|static inline void _downAp7(CoordIJK *ijk) {
  513|       |    // res r unit vectors in res r+1
  514|  8.47k|    CoordIJK iVec = {3, 0, 1};
  515|  8.47k|    CoordIJK jVec = {1, 3, 0};
  516|  8.47k|    CoordIJK kVec = {0, 1, 3};
  517|       |
  518|  8.47k|    _ijkScale(&iVec, ijk->i);
  519|  8.47k|    _ijkScale(&jVec, ijk->j);
  520|  8.47k|    _ijkScale(&kVec, ijk->k);
  521|       |
  522|  8.47k|    _ijkAdd(&iVec, &jVec, ijk);
  523|  8.47k|    _ijkAdd(ijk, &kVec, ijk);
  524|       |
  525|  8.47k|    _ijkNormalize(ijk);
  526|  8.47k|}
h3Index.c:_ijkScale:
  155|  50.6k|static inline void _ijkScale(CoordIJK *c, int factor) {
  156|  50.6k|    c->i *= factor;
  157|  50.6k|    c->j *= factor;
  158|  50.6k|    c->k *= factor;
  159|  50.6k|}
h3Index.c:_ijkAdd:
  129|  45.5k|                           CoordIJK *sum) {
  130|  45.5k|    sum->i = h1->i + h2->i;
  131|  45.5k|    sum->j = h1->j + h2->j;
  132|  45.5k|    sum->k = h1->k + h2->k;
  133|  45.5k|}
h3Index.c:_upAp7r:
  494|    597|static inline void _upAp7r(CoordIJK *ijk) {
  495|       |    // convert to CoordIJ
  496|    597|    int i = ijk->i - ijk->k;
  497|    597|    int j = ijk->j - ijk->k;
  498|       |
  499|    597|    ijk->i = (int)lround((2 * i + j) * M_ONESEVENTH);
  ------------------
  |  |   54|    597|#define M_ONESEVENTH 0.14285714285714285714285714285714285
  ------------------
  500|    597|    ijk->j = (int)lround((3 * j - i) * M_ONESEVENTH);
  ------------------
  |  |   54|    597|#define M_ONESEVENTH 0.14285714285714285714285714285714285
  ------------------
  501|    597|    ijk->k = 0;
  502|    597|    _ijkNormalize(ijk);
  503|    597|}
h3Index.c:_downAp7r:
  534|  8.40k|static inline void _downAp7r(CoordIJK *ijk) {
  535|       |    // res r unit vectors in res r+1
  536|  8.40k|    CoordIJK iVec = {3, 1, 0};
  537|  8.40k|    CoordIJK jVec = {0, 3, 1};
  538|  8.40k|    CoordIJK kVec = {1, 0, 3};
  539|       |
  540|  8.40k|    _ijkScale(&iVec, ijk->i);
  541|  8.40k|    _ijkScale(&jVec, ijk->j);
  542|  8.40k|    _ijkScale(&kVec, ijk->k);
  543|       |
  544|  8.40k|    _ijkAdd(&iVec, &jVec, ijk);
  545|  8.40k|    _ijkAdd(ijk, &kVec, ijk);
  546|       |
  547|  8.40k|    _ijkNormalize(ijk);
  548|  8.40k|}
h3Index.c:_ijkNormalize:
  207|  29.2k|static inline void _ijkNormalize(CoordIJK *c) {
  208|       |    // remove any negative values
  209|  29.2k|    if (c->i < 0) {
  ------------------
  |  Branch (209:9): [True: 232, False: 29.0k]
  ------------------
  210|    232|        c->j -= c->i;
  211|    232|        c->k -= c->i;
  212|    232|        c->i = 0;
  213|    232|    }
  214|       |
  215|  29.2k|    if (c->j < 0) {
  ------------------
  |  Branch (215:9): [True: 190, False: 29.0k]
  ------------------
  216|    190|        c->i -= c->j;
  217|    190|        c->k -= c->j;
  218|    190|        c->j = 0;
  219|    190|    }
  220|       |
  221|  29.2k|    if (c->k < 0) {
  ------------------
  |  Branch (221:9): [True: 0, False: 29.2k]
  ------------------
  222|      0|        c->i -= c->k;
  223|      0|        c->j -= c->k;
  224|      0|        c->k = 0;
  225|      0|    }
  226|       |
  227|       |    // remove the min value if needed
  228|  29.2k|    int min = c->i;
  229|  29.2k|    if (c->j < min) min = c->j;
  ------------------
  |  Branch (229:9): [True: 19.2k, False: 9.96k]
  ------------------
  230|  29.2k|    if (c->k < min) min = c->k;
  ------------------
  |  Branch (230:9): [True: 9.36k, False: 19.8k]
  ------------------
  231|  29.2k|    if (min > 0) {
  ------------------
  |  Branch (231:9): [True: 19.7k, False: 9.51k]
  ------------------
  232|  19.7k|        c->i -= min;
  233|  19.7k|        c->j -= min;
  234|  19.7k|        c->k -= min;
  235|  19.7k|    }
  236|  29.2k|}
h3Index.c:_neighbor:
  602|  15.7k|static inline void _neighbor(CoordIJK *ijk, Direction digit) {
  603|  15.7k|    if (digit > CENTER_DIGIT && digit < NUM_DIGITS) {
  ------------------
  |  Branch (603:9): [True: 12.1k, False: 3.64k]
  |  Branch (603:33): [True: 11.7k, False: 369]
  ------------------
  604|  11.7k|        _ijkAdd(ijk, &UNIT_VECS[digit], ijk);
  605|  11.7k|        _ijkNormalize(ijk);
  606|  11.7k|    }
  607|  15.7k|}
faceijk.c:_ijkRotate60ccw:
  614|  3.94k|static inline void _ijkRotate60ccw(CoordIJK *ijk) {
  615|       |    // unit vector rotations
  616|  3.94k|    CoordIJK iVec = {1, 1, 0};
  617|  3.94k|    CoordIJK jVec = {0, 1, 1};
  618|  3.94k|    CoordIJK kVec = {1, 0, 1};
  619|       |
  620|  3.94k|    _ijkScale(&iVec, ijk->i);
  621|  3.94k|    _ijkScale(&jVec, ijk->j);
  622|  3.94k|    _ijkScale(&kVec, ijk->k);
  623|       |
  624|  3.94k|    _ijkAdd(&iVec, &jVec, ijk);
  625|  3.94k|    _ijkAdd(ijk, &kVec, ijk);
  626|       |
  627|  3.94k|    _ijkNormalize(ijk);
  628|  3.94k|}
faceijk.c:_ijkScale:
  155|  18.8k|static inline void _ijkScale(CoordIJK *c, int factor) {
  156|  18.8k|    c->i *= factor;
  157|  18.8k|    c->j *= factor;
  158|  18.8k|    c->k *= factor;
  159|  18.8k|}
faceijk.c:_ijkAdd:
  129|  16.8k|                           CoordIJK *sum) {
  130|  16.8k|    sum->i = h1->i + h2->i;
  131|  16.8k|    sum->j = h1->j + h2->j;
  132|  16.8k|    sum->k = h1->k + h2->k;
  133|  16.8k|}
faceijk.c:_ijkNormalize:
  207|  10.8k|static inline void _ijkNormalize(CoordIJK *c) {
  208|       |    // remove any negative values
  209|  10.8k|    if (c->i < 0) {
  ------------------
  |  Branch (209:9): [True: 0, False: 10.8k]
  ------------------
  210|      0|        c->j -= c->i;
  211|      0|        c->k -= c->i;
  212|      0|        c->i = 0;
  213|      0|    }
  214|       |
  215|  10.8k|    if (c->j < 0) {
  ------------------
  |  Branch (215:9): [True: 0, False: 10.8k]
  ------------------
  216|      0|        c->i -= c->j;
  217|      0|        c->k -= c->j;
  218|      0|        c->j = 0;
  219|      0|    }
  220|       |
  221|  10.8k|    if (c->k < 0) {
  ------------------
  |  Branch (221:9): [True: 0, False: 10.8k]
  ------------------
  222|      0|        c->i -= c->k;
  223|      0|        c->j -= c->k;
  224|      0|        c->k = 0;
  225|      0|    }
  226|       |
  227|       |    // remove the min value if needed
  228|  10.8k|    int min = c->i;
  229|  10.8k|    if (c->j < min) min = c->j;
  ------------------
  |  Branch (229:9): [True: 5.03k, False: 5.84k]
  ------------------
  230|  10.8k|    if (c->k < min) min = c->k;
  ------------------
  |  Branch (230:9): [True: 3.96k, False: 6.92k]
  ------------------
  231|  10.8k|    if (min > 0) {
  ------------------
  |  Branch (231:9): [True: 9.32k, False: 1.56k]
  ------------------
  232|  9.32k|        c->i -= min;
  233|  9.32k|        c->j -= min;
  234|  9.32k|        c->k -= min;
  235|  9.32k|    }
  236|  10.8k|}
faceijk.c:_downAp3:
  557|    629|static inline void _downAp3(CoordIJK *ijk) {
  558|       |    // res r unit vectors in res r+1
  559|    629|    CoordIJK iVec = {2, 0, 1};
  560|    629|    CoordIJK jVec = {1, 2, 0};
  561|    629|    CoordIJK kVec = {0, 1, 2};
  562|       |
  563|    629|    _ijkScale(&iVec, ijk->i);
  564|    629|    _ijkScale(&jVec, ijk->j);
  565|    629|    _ijkScale(&kVec, ijk->k);
  566|       |
  567|    629|    _ijkAdd(&iVec, &jVec, ijk);
  568|    629|    _ijkAdd(ijk, &kVec, ijk);
  569|       |
  570|    629|    _ijkNormalize(ijk);
  571|    629|}
faceijk.c:_downAp3r:
  579|    629|static inline void _downAp3r(CoordIJK *ijk) {
  580|       |    // res r unit vectors in res r+1
  581|    629|    CoordIJK iVec = {2, 1, 0};
  582|    629|    CoordIJK jVec = {0, 2, 1};
  583|    629|    CoordIJK kVec = {1, 0, 2};
  584|       |
  585|    629|    _ijkScale(&iVec, ijk->i);
  586|    629|    _ijkScale(&jVec, ijk->j);
  587|    629|    _ijkScale(&kVec, ijk->k);
  588|       |
  589|    629|    _ijkAdd(&iVec, &jVec, ijk);
  590|    629|    _ijkAdd(ijk, &kVec, ijk);
  591|       |
  592|    629|    _ijkNormalize(ijk);
  593|    629|}
faceijk.c:_downAp7r:
  534|    515|static inline void _downAp7r(CoordIJK *ijk) {
  535|       |    // res r unit vectors in res r+1
  536|    515|    CoordIJK iVec = {3, 1, 0};
  537|    515|    CoordIJK jVec = {0, 3, 1};
  538|    515|    CoordIJK kVec = {1, 0, 3};
  539|       |
  540|    515|    _ijkScale(&iVec, ijk->i);
  541|    515|    _ijkScale(&jVec, ijk->j);
  542|    515|    _ijkScale(&kVec, ijk->k);
  543|       |
  544|    515|    _ijkAdd(&iVec, &jVec, ijk);
  545|    515|    _ijkAdd(ijk, &kVec, ijk);
  546|       |
  547|    515|    _ijkNormalize(ijk);
  548|    515|}
faceijk.c:_setIJK:
  103|    126|static inline void _setIJK(CoordIJK *ijk, int i, int j, int k) {
  104|    126|    ijk->i = i;
  105|    126|    ijk->j = j;
  106|    126|    ijk->k = k;
  107|    126|}
faceijk.c:_ijkSub:
  143|    126|                           CoordIJK *diff) {
  144|    126|    diff->i = h1->i - h2->i;
  145|    126|    diff->j = h1->j - h2->j;
  146|    126|    diff->k = h1->k - h2->k;
  147|    126|}
faceijk.c:_ijkRotate60cw:
  635|    126|static inline void _ijkRotate60cw(CoordIJK *ijk) {
  636|       |    // unit vector rotations
  637|    126|    CoordIJK iVec = {1, 0, 1};
  638|    126|    CoordIJK jVec = {1, 1, 0};
  639|    126|    CoordIJK kVec = {0, 1, 1};
  640|       |
  641|    126|    _ijkScale(&iVec, ijk->i);
  642|    126|    _ijkScale(&jVec, ijk->j);
  643|    126|    _ijkScale(&kVec, ijk->k);
  644|       |
  645|    126|    _ijkAdd(&iVec, &jVec, ijk);
  646|    126|    _ijkAdd(ijk, &kVec, ijk);
  647|       |
  648|    126|    _ijkNormalize(ijk);
  649|    126|}

h3NeighborRotations:
  451|    689|                            H3Index *out) {
  452|    689|    H3Index current = origin;
  453|       |
  454|    689|    if (dir < CENTER_DIGIT || dir >= INVALID_DIGIT) {
  ------------------
  |  Branch (454:9): [True: 0, False: 689]
  |  Branch (454:31): [True: 0, False: 689]
  ------------------
  455|      0|        return E_FAILED;
  456|      0|    }
  457|       |    // Ensure that rotations is modulo'd by 6 before any possible addition,
  458|       |    // to protect against signed integer overflow.
  459|    689|    *rotations = *rotations % 6;
  460|    689|    for (int i = 0; i < *rotations; i++) {
  ------------------
  |  Branch (460:21): [True: 0, False: 689]
  ------------------
  461|      0|        dir = _rotate60ccw(dir);
  462|      0|    }
  463|       |
  464|    689|    int newRotations = 0;
  465|    689|    int oldBaseCell = H3_GET_BASE_CELL(current);
  ------------------
  |  |  118|    689|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|    689|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|    689|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|    689|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  466|    689|    if (NEVER(oldBaseCell < 0) || oldBaseCell >= NUM_BASE_CELLS) {
  ------------------
  |  |  119|  1.37k|#define NEVER(X) ((X) ? (assert(0), 1) : 0)
  |  |  ------------------
  |  |  |  Branch (119:18): [True: 0, False: 689]
  |  |  |  Branch (119:19): [True: 0, False: 689]
  |  |  ------------------
  ------------------
                  if (NEVER(oldBaseCell < 0) || oldBaseCell >= NUM_BASE_CELLS) {
  ------------------
  |  |   81|    689|#define NUM_BASE_CELLS 122
  ------------------
  |  Branch (466:9): [Folded, False: 0]
  |  Branch (466:9): [Folded, False: 0]
  |  Branch (466:35): [True: 0, False: 689]
  ------------------
  467|       |        // Base cells less than zero can not be represented in an index
  468|      0|        return E_CELL_INVALID;
  469|      0|    }
  470|    689|    Direction oldLeadingDigit = _h3LeadingNonZeroDigit(current);
  471|       |
  472|       |    // Adjust the indexing digits and, if needed, the base cell.
  473|    689|    int r = H3_GET_RESOLUTION(current) - 1;
  ------------------
  |  |  129|    689|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    689|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    689|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    689|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  474|  3.09k|    while (true) {
  ------------------
  |  Branch (474:12): [True: 3.09k, Folded]
  ------------------
  475|  3.09k|        if (r == -1) {
  ------------------
  |  Branch (475:13): [True: 159, False: 2.93k]
  ------------------
  476|    159|            H3_SET_BASE_CELL(current, baseCellNeighbors[oldBaseCell][dir]);
  ------------------
  |  |  124|    159|    (h3) = (((h3)&H3_BC_MASK_NEGATIVE) | (((uint64_t)(bc)) << H3_BC_OFFSET))
  |  |  ------------------
  |  |  |  |   65|    159|#define H3_BC_MASK_NEGATIVE (~H3_BC_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   62|    159|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   38|    159|#define H3_BC_OFFSET 45
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_BC_MASK_NEGATIVE) | (((uint64_t)(bc)) << H3_BC_OFFSET))
  |  |  ------------------
  |  |  |  |   38|    159|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  477|    159|            newRotations = baseCellNeighbor60CCWRots[oldBaseCell][dir];
  478|       |
  479|    159|            if (H3_GET_BASE_CELL(current) == INVALID_BASE_CELL) {
  ------------------
  |  |  118|    159|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|    159|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|    159|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|    159|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
                          if (H3_GET_BASE_CELL(current) == INVALID_BASE_CELL) {
  ------------------
  |  |   38|    159|#define INVALID_BASE_CELL 127
  ------------------
  |  Branch (479:17): [True: 5, False: 154]
  ------------------
  480|       |                // Adjust for the deleted k vertex at the base cell level.
  481|       |                // This edge actually borders a different neighbor.
  482|      5|                H3_SET_BASE_CELL(current,
  ------------------
  |  |  124|      5|    (h3) = (((h3)&H3_BC_MASK_NEGATIVE) | (((uint64_t)(bc)) << H3_BC_OFFSET))
  |  |  ------------------
  |  |  |  |   65|      5|#define H3_BC_MASK_NEGATIVE (~H3_BC_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   62|      5|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   38|      5|#define H3_BC_OFFSET 45
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_BC_MASK_NEGATIVE) | (((uint64_t)(bc)) << H3_BC_OFFSET))
  |  |  ------------------
  |  |  |  |   38|      5|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  483|      5|                                 baseCellNeighbors[oldBaseCell][IK_AXES_DIGIT]);
  484|      5|                newRotations =
  485|      5|                    baseCellNeighbor60CCWRots[oldBaseCell][IK_AXES_DIGIT];
  486|       |
  487|       |                // perform the adjustment for the k-subsequence we're skipping
  488|       |                // over.
  489|      5|                current = _h3Rotate60ccw(current);
  490|      5|                *rotations = *rotations + 1;
  491|      5|            }
  492|       |
  493|    159|            break;
  494|  2.93k|        } else {
  495|  2.93k|            Direction oldDigit = H3_GET_INDEX_DIGIT(current, r + 1);
  ------------------
  |  |  141|  2.93k|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|  2.93k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|  2.93k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|  2.93k|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|  2.93k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  496|  2.93k|            Direction nextDir;
  497|  2.93k|            if (oldDigit == INVALID_DIGIT) {
  ------------------
  |  Branch (497:17): [True: 0, False: 2.93k]
  ------------------
  498|       |                // Only possible on invalid input
  499|      0|                return E_CELL_INVALID;
  500|  2.93k|            } else if (isResolutionClassIII(r + 1)) {
  ------------------
  |  Branch (500:24): [True: 1.61k, False: 1.31k]
  ------------------
  501|  1.61k|                H3_SET_INDEX_DIGIT(current, r + 1, NEW_DIGIT_II[oldDigit][dir]);
  ------------------
  |  |  162|  1.61k|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|  1.61k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|  1.61k|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|  1.61k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|  1.61k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|  1.61k|            (((uint64_t)(digit))                                            \
  |  |  165|  1.61k|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|  1.61k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|  1.61k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  502|  1.61k|                nextDir = NEW_ADJUSTMENT_II[oldDigit][dir];
  503|  1.61k|            } else {
  504|  1.31k|                H3_SET_INDEX_DIGIT(current, r + 1,
  ------------------
  |  |  162|  1.31k|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|  1.31k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|  1.31k|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|  1.31k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|  1.31k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|  1.31k|            (((uint64_t)(digit))                                            \
  |  |  165|  1.31k|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|  1.31k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|  1.31k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  505|  1.31k|                                   NEW_DIGIT_III[oldDigit][dir]);
  506|  1.31k|                nextDir = NEW_ADJUSTMENT_III[oldDigit][dir];
  507|  1.31k|            }
  508|       |
  509|  2.93k|            if (nextDir != CENTER_DIGIT) {
  ------------------
  |  Branch (509:17): [True: 2.40k, False: 530]
  ------------------
  510|  2.40k|                dir = nextDir;
  511|  2.40k|                r--;
  512|  2.40k|            } else {
  513|       |                // No more adjustment to perform
  514|    530|                break;
  515|    530|            }
  516|  2.93k|        }
  517|  3.09k|    }
  518|       |
  519|    689|    int newBaseCell = H3_GET_BASE_CELL(current);
  ------------------
  |  |  118|    689|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|    689|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|    689|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|    689|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  520|    689|    if (_isBaseCellPentagon(newBaseCell)) {
  ------------------
  |  Branch (520:9): [True: 402, False: 287]
  ------------------
  521|    402|        int alreadyAdjustedKSubsequence = 0;
  522|       |
  523|       |        // force rotation out of missing k-axes sub-sequence
  524|    402|        if (_h3LeadingNonZeroDigit(current) == K_AXES_DIGIT) {
  ------------------
  |  Branch (524:13): [True: 59, False: 343]
  ------------------
  525|     59|            if (oldBaseCell != newBaseCell) {
  ------------------
  |  Branch (525:17): [True: 24, False: 35]
  ------------------
  526|       |                // in this case, we traversed into the deleted
  527|       |                // k subsequence of a pentagon base cell.
  528|       |                // We need to rotate out of that case depending
  529|       |                // on how we got here.
  530|       |                // check for a cw/ccw offset face; default is ccw
  531|       |
  532|     24|                if (ALWAYS(_baseCellIsCwOffset(
  ------------------
  |  |  118|     24|#define ALWAYS(X) ((X) ? 1 : (assert(0), 0))
  |  |  ------------------
  |  |  |  Branch (118:19): [True: 24, False: 0]
  |  |  |  Branch (118:20): [True: 24, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (532:21): [Folded, False: 0]
  |  Branch (532:21): [Folded, False: 0]
  ------------------
  533|     24|                        newBaseCell,
  534|     24|                        baseCellData[oldBaseCell].homeFijk.face))) {
  535|     24|                    current = _h3Rotate60cw(current);
  536|     24|                } else {
  537|       |                    // See cwOffsetPent in testGridDisk.c for why this is
  538|       |                    // unreachable.
  539|      0|                    current = _h3Rotate60ccw(current);
  540|      0|                }
  541|     24|                alreadyAdjustedKSubsequence = 1;
  542|     35|            } else {
  543|       |                // In this case, we traversed into the deleted
  544|       |                // k subsequence from within the same pentagon
  545|       |                // base cell.
  546|     35|                if (oldLeadingDigit == CENTER_DIGIT) {
  ------------------
  |  Branch (546:21): [True: 0, False: 35]
  ------------------
  547|       |                    // Undefined: the k direction is deleted from here
  548|      0|                    return E_PENTAGON;
  549|     35|                } else if (oldLeadingDigit == JK_AXES_DIGIT) {
  ------------------
  |  Branch (549:28): [True: 14, False: 21]
  ------------------
  550|       |                    // Rotate out of the deleted k subsequence
  551|       |                    // We also need an additional change to the direction we're
  552|       |                    // moving in
  553|     14|                    current = _h3Rotate60ccw(current);
  554|     14|                    *rotations = *rotations + 1;
  555|     21|                } else if (oldLeadingDigit == IK_AXES_DIGIT) {
  ------------------
  |  Branch (555:28): [True: 21, False: 0]
  ------------------
  556|       |                    // Rotate out of the deleted k subsequence
  557|       |                    // We also need an additional change to the direction we're
  558|       |                    // moving in
  559|     21|                    current = _h3Rotate60cw(current);
  560|     21|                    *rotations = *rotations + 5;
  561|     21|                } else {
  562|       |                    // Could occur on invalid inputs that were already within
  563|       |                    // the deleted k subsequence
  564|      0|                    return E_FAILED;
  565|      0|                }
  566|     35|            }
  567|     59|        }
  568|       |
  569|    507|        for (int i = 0; i < newRotations; i++)
  ------------------
  |  Branch (569:25): [True: 105, False: 402]
  ------------------
  570|    105|            current = _h3RotatePent60ccw(current);
  571|       |
  572|       |        // Account for differing orientation of the base cells (this edge
  573|       |        // might not follow properties of some other edges.)
  574|    402|        if (oldBaseCell != newBaseCell) {
  ------------------
  |  Branch (574:13): [True: 69, False: 333]
  ------------------
  575|     69|            if (_isBaseCellPolarPentagon(newBaseCell)) {
  ------------------
  |  Branch (575:17): [True: 29, False: 40]
  ------------------
  576|       |                // 'polar' base cells behave differently because they have all
  577|       |                // i neighbors.
  578|     29|                if (oldBaseCell != 118 && oldBaseCell != 8 &&
  ------------------
  |  Branch (578:21): [True: 22, False: 7]
  |  Branch (578:43): [True: 14, False: 8]
  ------------------
  579|     14|                    _h3LeadingNonZeroDigit(current) != JK_AXES_DIGIT) {
  ------------------
  |  Branch (579:21): [True: 9, False: 5]
  ------------------
  580|      9|                    *rotations = *rotations + 1;
  581|      9|                }
  582|     40|            } else if (_h3LeadingNonZeroDigit(current) == IK_AXES_DIGIT &&
  ------------------
  |  Branch (582:24): [True: 25, False: 15]
  ------------------
  583|     25|                       !alreadyAdjustedKSubsequence) {
  ------------------
  |  Branch (583:24): [True: 7, False: 18]
  ------------------
  584|       |                // account for distortion introduced to the 5 neighbor by the
  585|       |                // deleted k subsequence.
  586|      7|                *rotations = *rotations + 1;
  587|      7|            }
  588|     69|        }
  589|    402|    } else {
  590|    428|        for (int i = 0; i < newRotations; i++)
  ------------------
  |  Branch (590:25): [True: 141, False: 287]
  ------------------
  591|    141|            current = _h3Rotate60ccw(current);
  592|    287|    }
  593|       |
  594|    689|    *rotations = (*rotations + newRotations) % 6;
  595|    689|    *out = current;
  596|       |
  597|    689|    return E_SUCCESS;
  598|    689|}
directionForNeighbor:
  608|     31|Direction directionForNeighbor(H3Index origin, H3Index destination) {
  609|     31|    bool isPent = H3_EXPORT(isPentagon)(origin);
  ------------------
  |  |   36|     31|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|     31|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|     31|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  610|       |    // Checks each neighbor, in order, to determine which direction the
  611|       |    // destination neighbor is located. Skips CENTER_DIGIT since that
  612|       |    // would be the origin; skips deleted K direction for pentagons.
  613|     31|    for (Direction direction = isPent ? J_AXES_DIGIT : K_AXES_DIGIT;
  ------------------
  |  Branch (613:32): [True: 31, False: 0]
  ------------------
  614|    124|         direction < NUM_DIGITS; direction++) {
  ------------------
  |  Branch (614:10): [True: 124, False: 0]
  ------------------
  615|    124|        H3Index neighbor;
  616|    124|        int rotations = 0;
  617|    124|        H3Error neighborError =
  618|    124|            h3NeighborRotations(origin, direction, &rotations, &neighbor);
  619|    124|        if (!neighborError && neighbor == destination) {
  ------------------
  |  Branch (619:13): [True: 124, False: 0]
  |  Branch (619:31): [True: 31, False: 93]
  ------------------
  620|     31|            return direction;
  621|     31|        }
  622|    124|    }
  623|      0|    return INVALID_DIGIT;
  624|     31|}

_isBaseCellPentagon:
  824|  10.1k|int _isBaseCellPentagon(int baseCell) {
  825|  10.1k|    if (baseCell < 0 || baseCell >= NUM_BASE_CELLS) {
  ------------------
  |  |   81|  10.1k|#define NUM_BASE_CELLS 122
  ------------------
  |  Branch (825:9): [True: 0, False: 10.1k]
  |  Branch (825:25): [True: 10, False: 10.1k]
  ------------------
  826|       |        // Base cells less than zero can not be represented in an index
  827|     10|        return false;
  828|     10|    }
  829|  10.1k|    return baseCellData[baseCell].isPentagon;
  830|  10.1k|}
_isBaseCellPolarPentagon:
  834|    347|bool _isBaseCellPolarPentagon(int baseCell) {
  835|    347|    return baseCell == 4 || baseCell == 117;
  ------------------
  |  Branch (835:12): [True: 55, False: 292]
  |  Branch (835:29): [True: 75, False: 217]
  ------------------
  836|    347|}
_baseCellToFaceIjk:
  866|    778|void _baseCellToFaceIjk(int baseCell, FaceIJK *h) {
  867|    778|    *h = baseCellData[baseCell].homeFijk;
  868|    778|}
_baseCellToCCWrot60:
  877|    778|int _baseCellToCCWrot60(int baseCell, int face) {
  878|    778|    if (face < 0 || face >= NUM_ICOSA_FACES) return INVALID_ROTATIONS;
  ------------------
  |  |   79|    778|#define NUM_ICOSA_FACES 20
  ------------------
                  if (face < 0 || face >= NUM_ICOSA_FACES) return INVALID_ROTATIONS;
  ------------------
  |  |   49|      0|#define INVALID_ROTATIONS -1
  ------------------
  |  Branch (878:9): [True: 0, False: 778]
  |  Branch (878:21): [True: 0, False: 778]
  ------------------
  879|  1.31k|    for (int i = 0; i < 3; i++) {
  ------------------
  |  Branch (879:21): [True: 1.31k, False: 0]
  ------------------
  880|  3.28k|        for (int j = 0; j < 3; j++) {
  ------------------
  |  Branch (880:25): [True: 2.74k, False: 535]
  ------------------
  881|  8.95k|            for (int k = 0; k < 3; k++) {
  ------------------
  |  Branch (881:29): [True: 6.99k, False: 1.96k]
  ------------------
  882|  6.99k|                if (faceIjkBaseCells[face][i][j][k].baseCell == baseCell) {
  ------------------
  |  Branch (882:21): [True: 778, False: 6.21k]
  ------------------
  883|    778|                    return faceIjkBaseCells[face][i][j][k].ccwRot60;
  884|    778|                }
  885|  6.99k|            }
  886|  2.74k|        }
  887|  1.31k|    }
  888|      0|    return INVALID_ROTATIONS;
  ------------------
  |  |   49|      0|#define INVALID_ROTATIONS -1
  ------------------
  889|    778|}
_baseCellIsCwOffset:
  893|     24|bool _baseCellIsCwOffset(int baseCell, int testFace) {
  894|     24|    return baseCellData[baseCell].cwOffsetPent[0] == testFace ||
  ------------------
  |  Branch (894:12): [True: 5, False: 19]
  ------------------
  895|     19|           baseCellData[baseCell].cwOffsetPent[1] == testFace;
  ------------------
  |  Branch (895:12): [True: 19, False: 0]
  ------------------
  896|     24|}

getDirectedEdgeOrigin:
  156|    371|H3Error H3_EXPORT(getDirectedEdgeOrigin)(H3Index edge, H3Index *out) {
  157|    371|    if (H3_GET_MODE(edge) != H3_DIRECTEDEDGE_MODE) {
  ------------------
  |  |  107|    371|#define H3_GET_MODE(h3) ((int)((((h3)&H3_MODE_MASK) >> H3_MODE_OFFSET)))
  |  |  ------------------
  |  |  |  |   56|    371|#define H3_MODE_MASK ((uint64_t)(15) << H3_MODE_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   35|    371|#define H3_MODE_OFFSET 59
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_MODE(h3) ((int)((((h3)&H3_MODE_MASK) >> H3_MODE_OFFSET)))
  |  |  ------------------
  |  |  |  |   35|    371|#define H3_MODE_OFFSET 59
  |  |  ------------------
  ------------------
                  if (H3_GET_MODE(edge) != H3_DIRECTEDEDGE_MODE) {
  ------------------
  |  |   91|    371|#define H3_DIRECTEDEDGE_MODE 2
  ------------------
  |  Branch (157:9): [True: 351, False: 20]
  ------------------
  158|    351|        return E_DIR_EDGE_INVALID;
  159|    351|    }
  160|     20|    H3Index origin = edge;
  161|     20|    H3_SET_MODE(origin, H3_CELL_MODE);
  ------------------
  |  |  113|     20|    (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   59|     20|#define H3_MODE_MASK_NEGATIVE (~H3_MODE_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   56|     20|#define H3_MODE_MASK ((uint64_t)(15) << H3_MODE_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   35|     20|#define H3_MODE_OFFSET 59
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   35|     20|#define H3_MODE_OFFSET 59
  |  |  ------------------
  ------------------
  162|     20|    H3_SET_RESERVED_BITS(origin, 0);
  ------------------
  |  |  149|     20|    (h3) = (((h3)&H3_RESERVED_MASK_NEGATIVE) | \
  |  |  ------------------
  |  |  |  |   77|     20|#define H3_RESERVED_MASK_NEGATIVE (~H3_RESERVED_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   74|     20|#define H3_RESERVED_MASK ((uint64_t)(7) << H3_RESERVED_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   44|     20|#define H3_RESERVED_OFFSET 56
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  150|     20|            (((uint64_t)(v)) << H3_RESERVED_OFFSET))
  |  |  ------------------
  |  |  |  |   44|     20|#define H3_RESERVED_OFFSET 56
  |  |  ------------------
  ------------------
  163|     20|    *out = origin;
  164|     20|    return E_SUCCESS;
  165|    371|}
isValidDirectedEdge:
  189|    585|int H3_EXPORT(isValidDirectedEdge)(H3Index edge) {
  190|    585|    Direction neighborDirection = H3_GET_RESERVED_BITS(edge);
  ------------------
  |  |  156|    585|    ((int)((((h3)&H3_RESERVED_MASK) >> H3_RESERVED_OFFSET)))
  |  |  ------------------
  |  |  |  |   74|    585|#define H3_RESERVED_MASK ((uint64_t)(7) << H3_RESERVED_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   44|    585|#define H3_RESERVED_OFFSET 56
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   ((int)((((h3)&H3_RESERVED_MASK) >> H3_RESERVED_OFFSET)))
  |  |  ------------------
  |  |  |  |   44|    585|#define H3_RESERVED_OFFSET 56
  |  |  ------------------
  ------------------
  191|    585|    if (neighborDirection <= CENTER_DIGIT || neighborDirection >= NUM_DIGITS) {
  ------------------
  |  Branch (191:9): [True: 192, False: 393]
  |  Branch (191:46): [True: 22, False: 371]
  ------------------
  192|    214|        return 0;
  193|    214|    }
  194|       |
  195|    371|    H3Index origin;
  196|       |    // Note: This call is also checking for H3_DIRECTEDEDGE_MODE
  197|    371|    H3Error originResult = H3_EXPORT(getDirectedEdgeOrigin)(edge, &origin);
  ------------------
  |  |   36|    371|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    371|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    371|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  198|    371|    if (originResult) {
  ------------------
  |  Branch (198:9): [True: 351, False: 20]
  ------------------
  199|    351|        return 0;
  200|    351|    }
  201|     20|    if (H3_EXPORT(isPentagon)(origin) && neighborDirection == K_AXES_DIGIT) {
  ------------------
  |  |   36|     20|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|     20|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|     20|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (201:9): [True: 5, False: 15]
  |  Branch (201:42): [True: 1, False: 4]
  ------------------
  202|      1|        return 0;
  203|      1|    }
  204|       |
  205|     19|    return H3_EXPORT(isValidCell)(origin);
  ------------------
  |  |   36|     19|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|     19|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|     19|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  206|     20|}

_faceIjkPentToVerts:
  642|     20|void _faceIjkPentToVerts(FaceIJK *fijk, int *res, FaceIJK *fijkVerts) {
  643|       |    // the vertexes of an origin-centered pentagon in a Class II resolution on a
  644|       |    // substrate grid with aperture sequence 33r. The aperture 3 gets us the
  645|       |    // vertices, and the 3r gets us back to Class II.
  646|       |    // vertices listed ccw from the i-axes
  647|     20|    CoordIJK vertsCII[NUM_PENT_VERTS] = {
  648|     20|        {2, 1, 0},  // 0
  649|     20|        {1, 2, 0},  // 1
  650|     20|        {0, 2, 1},  // 2
  651|     20|        {0, 1, 2},  // 3
  652|     20|        {1, 0, 2},  // 4
  653|     20|    };
  654|       |
  655|       |    // the vertexes of an origin-centered pentagon in a Class III resolution on
  656|       |    // a substrate grid with aperture sequence 33r7r. The aperture 3 gets us the
  657|       |    // vertices, and the 3r7r gets us to Class II. vertices listed ccw from the
  658|       |    // i-axes
  659|     20|    CoordIJK vertsCIII[NUM_PENT_VERTS] = {
  660|     20|        {5, 4, 0},  // 0
  661|     20|        {1, 5, 0},  // 1
  662|     20|        {0, 5, 4},  // 2
  663|     20|        {0, 1, 5},  // 3
  664|     20|        {4, 0, 5},  // 4
  665|     20|    };
  666|       |
  667|       |    // get the correct set of substrate vertices for this resolution
  668|     20|    CoordIJK *verts;
  669|     20|    if (isResolutionClassIII(*res))
  ------------------
  |  Branch (669:9): [True: 20, False: 0]
  ------------------
  670|     20|        verts = vertsCIII;
  671|      0|    else
  672|      0|        verts = vertsCII;
  673|       |
  674|       |    // adjust the center point to be in an aperture 33r substrate grid
  675|       |    // these should be composed for speed
  676|     20|    _downAp3(&fijk->coord);
  677|     20|    _downAp3r(&fijk->coord);
  678|       |
  679|       |    // if res is Class III we need to add a cw aperture 7 to get to
  680|       |    // icosahedral Class II
  681|     20|    if (isResolutionClassIII(*res)) {
  ------------------
  |  Branch (681:9): [True: 20, False: 0]
  ------------------
  682|     20|        _downAp7r(&fijk->coord);
  683|     20|        *res += 1;
  684|     20|    }
  685|       |
  686|       |    // The center point is now in the same substrate grid as the origin
  687|       |    // cell vertices. Add the center point substate coordinates
  688|       |    // to each vertex to translate the vertices to that cell.
  689|    120|    for (int v = 0; v < NUM_PENT_VERTS; v++) {
  ------------------
  |  |   85|    120|#define NUM_PENT_VERTS 5
  ------------------
  |  Branch (689:21): [True: 100, False: 20]
  ------------------
  690|    100|        fijkVerts[v].face = fijk->face;
  691|    100|        _ijkAdd(&fijk->coord, &verts[v], &fijkVerts[v].coord);
  692|    100|        _ijkNormalize(&fijkVerts[v].coord);
  693|    100|    }
  694|     20|}
_faceIjkToVerts:
  819|    609|void _faceIjkToVerts(FaceIJK *fijk, int *res, FaceIJK *fijkVerts) {
  820|       |    // the vertexes of an origin-centered cell in a Class II resolution on a
  821|       |    // substrate grid with aperture sequence 33r. The aperture 3 gets us the
  822|       |    // vertices, and the 3r gets us back to Class II.
  823|       |    // vertices listed ccw from the i-axes
  824|    609|    CoordIJK vertsCII[NUM_HEX_VERTS] = {
  825|    609|        {2, 1, 0},  // 0
  826|    609|        {1, 2, 0},  // 1
  827|    609|        {0, 2, 1},  // 2
  828|    609|        {0, 1, 2},  // 3
  829|    609|        {1, 0, 2},  // 4
  830|    609|        {2, 0, 1}   // 5
  831|    609|    };
  832|       |
  833|       |    // the vertexes of an origin-centered cell in a Class III resolution on a
  834|       |    // substrate grid with aperture sequence 33r7r. The aperture 3 gets us the
  835|       |    // vertices, and the 3r7r gets us to Class II.
  836|       |    // vertices listed ccw from the i-axes
  837|    609|    CoordIJK vertsCIII[NUM_HEX_VERTS] = {
  838|    609|        {5, 4, 0},  // 0
  839|    609|        {1, 5, 0},  // 1
  840|    609|        {0, 5, 4},  // 2
  841|    609|        {0, 1, 5},  // 3
  842|    609|        {4, 0, 5},  // 4
  843|    609|        {5, 0, 1}   // 5
  844|    609|    };
  845|       |
  846|       |    // get the correct set of substrate vertices for this resolution
  847|    609|    CoordIJK *verts;
  848|    609|    if (isResolutionClassIII(*res))
  ------------------
  |  Branch (848:9): [True: 495, False: 114]
  ------------------
  849|    495|        verts = vertsCIII;
  850|    114|    else
  851|    114|        verts = vertsCII;
  852|       |
  853|       |    // adjust the center point to be in an aperture 33r substrate grid
  854|       |    // these should be composed for speed
  855|    609|    _downAp3(&fijk->coord);
  856|    609|    _downAp3r(&fijk->coord);
  857|       |
  858|       |    // if res is Class III we need to add a cw aperture 7 to get to
  859|       |    // icosahedral Class II
  860|    609|    if (isResolutionClassIII(*res)) {
  ------------------
  |  Branch (860:9): [True: 495, False: 114]
  ------------------
  861|    495|        _downAp7r(&fijk->coord);
  862|    495|        *res += 1;
  863|    495|    }
  864|       |
  865|       |    // The center point is now in the same substrate grid as the origin
  866|       |    // cell vertices. Add the center point substate coordinates
  867|       |    // to each vertex to translate the vertices to that cell.
  868|  4.26k|    for (int v = 0; v < NUM_HEX_VERTS; v++) {
  ------------------
  |  |   83|  4.26k|#define NUM_HEX_VERTS 6
  ------------------
  |  Branch (868:21): [True: 3.65k, False: 609]
  ------------------
  869|  3.65k|        fijkVerts[v].face = fijk->face;
  870|  3.65k|        _ijkAdd(&fijk->coord, &verts[v], &fijkVerts[v].coord);
  871|  3.65k|        _ijkNormalize(&fijkVerts[v].coord);
  872|  3.65k|    }
  873|    609|}
_adjustOverageClassII:
  888|  6.06k|                              int substrate) {
  889|  6.06k|    Overage overage = NO_OVERAGE;
  890|       |
  891|  6.06k|    CoordIJK *ijk = &fijk->coord;
  892|       |
  893|       |    // get the maximum dimension value; scale if a substrate grid
  894|  6.06k|    int maxDim = maxDimByCIIres[res];
  895|  6.06k|    if (substrate) maxDim *= 3;
  ------------------
  |  Branch (895:9): [True: 3.87k, False: 2.19k]
  ------------------
  896|       |
  897|       |    // check for overage
  898|  6.06k|    if (substrate && ijk->i + ijk->j + ijk->k == maxDim)  // on edge
  ------------------
  |  Branch (898:9): [True: 3.87k, False: 2.19k]
  |  Branch (898:22): [True: 240, False: 3.63k]
  ------------------
  899|    240|        overage = FACE_EDGE;
  900|  5.82k|    else if (ijk->i + ijk->j + ijk->k > maxDim)  // overage
  ------------------
  |  Branch (900:14): [True: 1.28k, False: 4.54k]
  ------------------
  901|  1.28k|    {
  902|  1.28k|        overage = NEW_FACE;
  903|       |
  904|  1.28k|        const FaceOrientIJK *fijkOrient;
  905|  1.28k|        if (ijk->k > 0) {
  ------------------
  |  Branch (905:13): [True: 872, False: 414]
  ------------------
  906|    872|            if (ijk->j > 0)  // jk "quadrant"
  ------------------
  |  Branch (906:17): [True: 295, False: 577]
  ------------------
  907|    295|                fijkOrient = &faceNeighbors[fijk->face][JK];
  ------------------
  |  |   57|    295|#define JK 3
  ------------------
  908|    577|            else  // ik "quadrant"
  909|    577|            {
  910|    577|                fijkOrient = &faceNeighbors[fijk->face][KI];
  ------------------
  |  |   55|    577|#define KI 2
  ------------------
  911|       |
  912|       |                // adjust for the pentagonal missing sequence
  913|    577|                if (pentLeading4) {
  ------------------
  |  Branch (913:21): [True: 126, False: 451]
  ------------------
  914|       |                    // translate origin to center of pentagon
  915|    126|                    CoordIJK origin;
  916|    126|                    _setIJK(&origin, maxDim, 0, 0);
  917|    126|                    CoordIJK tmp;
  918|    126|                    _ijkSub(ijk, &origin, &tmp);
  919|       |                    // rotate to adjust for the missing sequence
  920|    126|                    _ijkRotate60cw(&tmp);
  921|       |                    // translate the origin back to the center of the triangle
  922|    126|                    _ijkAdd(&tmp, &origin, ijk);
  923|    126|                }
  924|    577|            }
  925|    872|        } else  // ij "quadrant"
  926|    414|            fijkOrient = &faceNeighbors[fijk->face][IJ];
  ------------------
  |  |   53|    414|#define IJ 1
  ------------------
  927|       |
  928|  1.28k|        fijk->face = fijkOrient->face;
  929|       |
  930|       |        // rotate and translate for adjacent face
  931|  5.23k|        for (int i = 0; i < fijkOrient->ccwRot60; i++) _ijkRotate60ccw(ijk);
  ------------------
  |  Branch (931:25): [True: 3.94k, False: 1.28k]
  ------------------
  932|       |
  933|  1.28k|        CoordIJK transVec = fijkOrient->translate;
  934|  1.28k|        int unitScale = unitScaleByCIIres[res];
  935|  1.28k|        if (substrate) unitScale *= 3;
  ------------------
  |  Branch (935:13): [True: 208, False: 1.07k]
  ------------------
  936|  1.28k|        _ijkScale(&transVec, unitScale);
  937|  1.28k|        _ijkAdd(ijk, &transVec, ijk);
  938|  1.28k|        _ijkNormalize(ijk);
  939|       |
  940|       |        // overage points on pentagon boundaries can end up on edges
  941|  1.28k|        if (substrate && ijk->i + ijk->j + ijk->k == maxDim)  // on edge
  ------------------
  |  Branch (941:13): [True: 208, False: 1.07k]
  |  Branch (941:26): [True: 2, False: 206]
  ------------------
  942|      2|            overage = FACE_EDGE;
  943|  1.28k|    }
  944|       |
  945|  6.06k|    return overage;
  946|  6.06k|}
_adjustPentVertOverage:
  956|    100|Overage _adjustPentVertOverage(FaceIJK *fijk, int res) {
  957|    100|    int pentLeading4 = 0;
  958|    100|    Overage overage;
  959|    220|    do {
  960|    220|        overage = _adjustOverageClassII(fijk, res, pentLeading4, 1);
  961|    220|    } while (overage == NEW_FACE);
  ------------------
  |  Branch (961:14): [True: 120, False: 100]
  ------------------
  962|    100|    return overage;
  963|    100|}

getResolution:
   87|    632|int H3_EXPORT(getResolution)(H3Index h) { return H3_GET_RESOLUTION(h); }
  ------------------
  |  |  129|    632|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    632|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    632|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    632|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
getBaseCellNumber:
   98|  1.41k|int H3_EXPORT(getBaseCellNumber)(H3Index h) { return H3_GET_BASE_CELL(h); }
  ------------------
  |  |  118|  1.41k|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|  1.41k|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|  1.41k|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|  1.41k|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
getIndexDigit:
  116|    632|H3Error H3_EXPORT(getIndexDigit)(H3Index h, int res, int *out) {
  117|    632|    if (res < 1 || res > MAX_H3_RES) {
  ------------------
  |  |   76|    363|#define MAX_H3_RES 15
  ------------------
  |  Branch (117:9): [True: 269, False: 363]
  |  Branch (117:20): [True: 347, False: 16]
  ------------------
  118|    616|        return E_RES_DOMAIN;
  119|    616|    }
  120|     16|    *out = H3_GET_INDEX_DIGIT(h, res);
  ------------------
  |  |  141|     16|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|     16|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|     16|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|     16|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|     16|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  121|     16|    return E_SUCCESS;
  122|    632|}
isValidCell:
  343|  1.63k|int H3_EXPORT(isValidCell)(H3Index h) {
  344|       |    /*
  345|       |    Look for bit patterns that would disqualify an H3Index from
  346|       |    being valid. If identified, exit early.
  347|       |
  348|       |    For reference the H3 index bit layout:
  349|       |
  350|       |    |   Region   | # bits |
  351|       |    |------------|--------|
  352|       |    | High       |      1 |
  353|       |    | Mode       |      4 |
  354|       |    | Reserved   |      3 |
  355|       |    | Resolution |      4 |
  356|       |    | Base Cell  |      7 |
  357|       |    | Digit 1    |      3 |
  358|       |    | Digit 2    |      3 |
  359|       |    | ...        |    ... |
  360|       |    | Digit 15   |      3 |
  361|       |
  362|       |    Speed benefits come from using bit manipulation instead of loops,
  363|       |    whenever possible.
  364|       |    */
  365|  1.63k|    if (!_hasGoodTopBits(h)) return false;
  ------------------
  |  Branch (365:9): [True: 1.01k, False: 625]
  ------------------
  366|       |
  367|       |    // No need to check resolution; any 4 bits give a valid resolution.
  368|    625|    const int res = H3_GET_RESOLUTION(h);
  ------------------
  |  |  129|    625|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    625|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    625|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    625|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  369|       |
  370|       |    // Get base cell number and check that it is valid.
  371|    625|    const int bc = H3_GET_BASE_CELL(h);
  ------------------
  |  |  118|    625|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|    625|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|    625|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|    625|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  372|    625|    if (bc >= NUM_BASE_CELLS) return false;
  ------------------
  |  |   81|    625|#define NUM_BASE_CELLS 122
  ------------------
  |  Branch (372:9): [True: 4, False: 621]
  ------------------
  373|       |
  374|    621|    if (_hasAny7UptoRes(h, res)) return false;
  ------------------
  |  Branch (374:9): [True: 73, False: 548]
  ------------------
  375|    548|    if (!_hasAll7AfterRes(h, res)) return false;
  ------------------
  |  Branch (375:9): [True: 112, False: 436]
  ------------------
  376|    436|    if (_hasDeletedSubsequence(h, bc)) return false;
  ------------------
  |  Branch (376:9): [True: 31, False: 405]
  ------------------
  377|       |
  378|       |    // If no disqualifications were identified, the index is a valid H3 cell.
  379|    405|    return true;
  380|    436|}
isValidIndex:
  388|    632|int H3_EXPORT(isValidIndex)(H3Index h) {
  389|    632|    return H3_EXPORT(isValidCell)(h) || H3_EXPORT(isValidDirectedEdge)(h) ||
  ------------------
  |  |   36|    632|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
                  return H3_EXPORT(isValidCell)(h) || H3_EXPORT(isValidDirectedEdge)(h) ||
  ------------------
  |  |   36|    585|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (389:12): [True: 47, False: 585]
  |  Branch (389:41): [True: 4, False: 581]
  ------------------
  390|    581|           H3_EXPORT(isValidVertex)(h);
  ------------------
  |  |   36|    581|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    632|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    632|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (390:12): [True: 88, False: 493]
  ------------------
  391|    632|}
makeDirectChild:
  483|     14|H3Index makeDirectChild(H3Index h, int cellNumber) {
  484|     14|    int childRes = H3_GET_RESOLUTION(h) + 1;
  ------------------
  |  |  129|     14|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|     14|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|     14|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|     14|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  485|     14|    H3Index childH = H3_SET_RESOLUTION(h, childRes);
  ------------------
  |  |  135|     14|    (h3) = (((h3)&H3_RES_MASK_NEGATIVE) | (((uint64_t)(res)) << H3_RES_OFFSET))
  |  |  ------------------
  |  |  |  |   71|     14|#define H3_RES_MASK_NEGATIVE (~H3_RES_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   68|     14|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   41|     14|#define H3_RES_OFFSET 52
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_RES_MASK_NEGATIVE) | (((uint64_t)(res)) << H3_RES_OFFSET))
  |  |  ------------------
  |  |  |  |   41|     14|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  486|     14|    H3_SET_INDEX_DIGIT(childH, childRes, cellNumber);
  ------------------
  |  |  162|     14|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|     14|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|     14|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|     14|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|     14|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|     14|            (((uint64_t)(digit))                                            \
  |  |  165|     14|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|     14|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|     14|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  487|     14|    return childH;
  488|     14|}
isResClassIII:
  834|    632|int H3_EXPORT(isResClassIII)(H3Index h) { return H3_GET_RESOLUTION(h) % 2; }
  ------------------
  |  |  129|    632|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    632|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    632|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    632|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
isPentagon:
  841|  3.88k|int H3_EXPORT(isPentagon)(H3Index h) {
  842|  3.88k|    return _isBaseCellPentagon(H3_GET_BASE_CELL(h)) &&
  ------------------
  |  |  118|  3.88k|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|  3.88k|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|  3.88k|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|  3.88k|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  |  Branch (842:12): [True: 1.90k, False: 1.98k]
  ------------------
  843|  1.90k|           !_h3LeadingNonZeroDigit(h);
  ------------------
  |  Branch (843:12): [True: 200, False: 1.70k]
  ------------------
  844|  3.88k|}
_h3LeadingNonZeroDigit:
  851|  5.25k|Direction _h3LeadingNonZeroDigit(H3Index h) {
  852|  17.9k|    for (int r = 1; r <= H3_GET_RESOLUTION(h); r++)
  ------------------
  |  |  129|  17.9k|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|  17.9k|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|  17.9k|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|  17.9k|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (852:21): [True: 17.4k, False: 567]
  ------------------
  853|  17.4k|        if (H3_GET_INDEX_DIGIT(h, r)) return H3_GET_INDEX_DIGIT(h, r);
  ------------------
  |  |  141|  17.4k|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|  17.4k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|  17.4k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  |  Branch (141:5): [True: 4.69k, False: 12.7k]
  |  |  ------------------
  |  |  142|  17.4k|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|  17.4k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
                      if (H3_GET_INDEX_DIGIT(h, r)) return H3_GET_INDEX_DIGIT(h, r);
  ------------------
  |  |  141|  4.69k|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|  4.69k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|  4.69k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|  4.69k|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|  4.69k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  854|       |
  855|       |    // if we're here it's all 0's
  856|    567|    return CENTER_DIGIT;
  857|  5.25k|}
_h3RotatePent60ccw:
  863|    105|H3Index _h3RotatePent60ccw(H3Index h) {
  864|       |    // rotate in place; skips any leading 1 digits (k-axis)
  865|       |
  866|    105|    int foundFirstNonZeroDigit = 0;
  867|    907|    for (int r = 1, res = H3_GET_RESOLUTION(h); r <= res; r++) {
  ------------------
  |  |  129|    105|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    105|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    105|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    105|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (867:49): [True: 802, False: 105]
  ------------------
  868|       |        // rotate this digit
  869|    802|        H3_SET_INDEX_DIGIT(h, r, _rotate60ccw(H3_GET_INDEX_DIGIT(h, r)));
  ------------------
  |  |  162|    802|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|    802|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|    802|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|    802|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|    802|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|    802|            (((uint64_t)(digit))                                            \
  |  |  165|    802|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|    802|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|    802|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  870|       |
  871|       |        // look for the first non-zero digit so we
  872|       |        // can adjust for deleted k-axes sequence
  873|       |        // if necessary
  874|    802|        if (!foundFirstNonZeroDigit && H3_GET_INDEX_DIGIT(h, r) != 0) {
  ------------------
  |  |  141|     86|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|     86|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|     86|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|     86|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|     86|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  |  Branch (874:13): [True: 86, False: 716]
  |  Branch (874:40): [True: 86, False: 0]
  ------------------
  875|     86|            foundFirstNonZeroDigit = 1;
  876|       |
  877|       |            // adjust for deleted k-axes sequence
  878|     86|            if (_h3LeadingNonZeroDigit(h) == K_AXES_DIGIT)
  ------------------
  |  Branch (878:17): [True: 37, False: 49]
  ------------------
  879|     37|                h = _h3Rotate60ccw(h);
  880|     86|        }
  881|    802|    }
  882|    105|    return h;
  883|    105|}
_h3Rotate60ccw:
  914|    197|H3Index _h3Rotate60ccw(H3Index h) {
  915|  1.07k|    for (int r = 1, res = H3_GET_RESOLUTION(h); r <= res; r++) {
  ------------------
  |  |  129|    197|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    197|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    197|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    197|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (915:49): [True: 877, False: 197]
  ------------------
  916|    877|        Direction oldDigit = H3_GET_INDEX_DIGIT(h, r);
  ------------------
  |  |  141|    877|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|    877|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|    877|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|    877|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|    877|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  917|    877|        H3_SET_INDEX_DIGIT(h, r, _rotate60ccw(oldDigit));
  ------------------
  |  |  162|    877|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|    877|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|    877|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|    877|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|    877|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|    877|            (((uint64_t)(digit))                                            \
  |  |  165|    877|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|    877|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|    877|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  918|    877|    }
  919|       |
  920|    197|    return h;
  921|    197|}
_h3Rotate60cw:
  927|    202|H3Index _h3Rotate60cw(H3Index h) {
  928|  2.38k|    for (int r = 1, res = H3_GET_RESOLUTION(h); r <= res; r++) {
  ------------------
  |  |  129|    202|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    202|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    202|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    202|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (928:49): [True: 2.17k, False: 202]
  ------------------
  929|  2.17k|        H3_SET_INDEX_DIGIT(h, r, _rotate60cw(H3_GET_INDEX_DIGIT(h, r)));
  ------------------
  |  |  162|  2.17k|    (h3) = (((h3) & ~((H3_DIGIT_MASK                                        \
  |  |  ------------------
  |  |  |  |   80|  2.17k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  |  |  163|  2.17k|                       << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   76|  2.17k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                                      << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))) | \
  |  |  ------------------
  |  |  |  |   47|  2.17k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  164|  2.17k|            (((uint64_t)(digit))                                            \
  |  |  165|  2.17k|             << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   76|  2.17k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                            << ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)))
  |  |  ------------------
  |  |  |  |   47|  2.17k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  ------------------
  930|  2.17k|    }
  931|       |
  932|    202|    return h;
  933|    202|}
_h3ToFaceIjkWithInitializedFijk:
 1086|  1.40k|int _h3ToFaceIjkWithInitializedFijk(H3Index h, FaceIJK *fijk) {
 1087|  1.40k|    CoordIJK *ijk = &fijk->coord;
 1088|  1.40k|    int res = H3_GET_RESOLUTION(h);
  ------------------
  |  |  129|  1.40k|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|  1.40k|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|  1.40k|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|  1.40k|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
 1089|       |
 1090|       |    // center base cell hierarchy is entirely on this face
 1091|  1.40k|    int possibleOverage = 1;
 1092|  1.40k|    if (!_isBaseCellPentagon(H3_GET_BASE_CELL(h)) &&
  ------------------
  |  |  118|  1.40k|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|  1.40k|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|  1.40k|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|  1.40k|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
  |  Branch (1092:9): [True: 735, False: 672]
  ------------------
 1093|    735|        (res == 0 ||
  ------------------
  |  Branch (1093:10): [True: 63, False: 672]
  ------------------
 1094|    672|         (fijk->coord.i == 0 && fijk->coord.j == 0 && fijk->coord.k == 0)))
  ------------------
  |  Branch (1094:11): [True: 423, False: 249]
  |  Branch (1094:33): [True: 169, False: 254]
  |  Branch (1094:55): [True: 66, False: 103]
  ------------------
 1095|    129|        possibleOverage = 0;
 1096|       |
 1097|  17.1k|    for (int r = 1; r <= res; r++) {
  ------------------
  |  Branch (1097:21): [True: 15.7k, False: 1.40k]
  ------------------
 1098|  15.7k|        if (isResolutionClassIII(r)) {
  ------------------
  |  Branch (1098:13): [True: 8.47k, False: 7.31k]
  ------------------
 1099|       |            // Class III == rotate ccw
 1100|  8.47k|            _downAp7(ijk);
 1101|  8.47k|        } else {
 1102|       |            // Class II == rotate cw
 1103|  7.31k|            _downAp7r(ijk);
 1104|  7.31k|        }
 1105|       |
 1106|  15.7k|        _neighbor(ijk, H3_GET_INDEX_DIGIT(h, r));
  ------------------
  |  |  141|  15.7k|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|  15.7k|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|  15.7k|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|  15.7k|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|  15.7k|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
 1107|  15.7k|    }
 1108|       |
 1109|  1.40k|    return possibleOverage;
 1110|  1.40k|}
_h3ToFaceIjk:
 1117|  1.41k|H3Error _h3ToFaceIjk(H3Index h, FaceIJK *fijk) {
 1118|  1.41k|    int baseCell = H3_GET_BASE_CELL(h);
  ------------------
  |  |  118|  1.41k|#define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   62|  1.41k|#define H3_BC_MASK ((uint64_t)(127) << H3_BC_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   38|  1.41k|#define H3_BC_OFFSET 45
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_BASE_CELL(h3) ((int)((((h3)&H3_BC_MASK) >> H3_BC_OFFSET)))
  |  |  ------------------
  |  |  |  |   38|  1.41k|#define H3_BC_OFFSET 45
  |  |  ------------------
  ------------------
 1119|  1.41k|    if (NEVER(baseCell < 0) || baseCell >= NUM_BASE_CELLS) {
  ------------------
  |  |  119|  2.82k|#define NEVER(X) ((X) ? (assert(0), 1) : 0)
  |  |  ------------------
  |  |  |  Branch (119:18): [True: 0, False: 1.41k]
  |  |  |  Branch (119:19): [True: 0, False: 1.41k]
  |  |  ------------------
  ------------------
                  if (NEVER(baseCell < 0) || baseCell >= NUM_BASE_CELLS) {
  ------------------
  |  |   81|  1.41k|#define NUM_BASE_CELLS 122
  ------------------
  |  Branch (1119:9): [Folded, False: 0]
  |  Branch (1119:9): [Folded, False: 0]
  |  Branch (1119:32): [True: 3, False: 1.40k]
  ------------------
 1120|       |        // Base cells less than zero can not be represented in an index
 1121|       |        // To prevent reading uninitialized memory, we zero the output.
 1122|      3|        fijk->face = 0;
 1123|      3|        fijk->coord.i = fijk->coord.j = fijk->coord.k = 0;
 1124|      3|        return E_CELL_INVALID;
 1125|      3|    }
 1126|       |    // adjust for the pentagonal missing sequence; all of sub-sequence 5 needs
 1127|       |    // to be adjusted (and some of sub-sequence 4 below)
 1128|  1.40k|    if (_isBaseCellPentagon(baseCell) && _h3LeadingNonZeroDigit(h) == 5)
  ------------------
  |  Branch (1128:9): [True: 672, False: 735]
  |  Branch (1128:42): [True: 157, False: 515]
  ------------------
 1129|    157|        h = _h3Rotate60cw(h);
 1130|       |
 1131|       |    // start with the "home" face and ijk+ coordinates for the base cell of c
 1132|  1.40k|    *fijk = baseCellData[baseCell].homeFijk;
 1133|  1.40k|    if (!_h3ToFaceIjkWithInitializedFijk(h, fijk))
  ------------------
  |  Branch (1133:9): [True: 129, False: 1.27k]
  ------------------
 1134|    129|        return E_SUCCESS;  // no overage is possible; h lies on this face
 1135|       |
 1136|       |    // if we're here we have the potential for an "overage"; i.e., it is
 1137|       |    // possible that c lies on an adjacent face
 1138|       |
 1139|  1.27k|    CoordIJK origIJK = fijk->coord;
 1140|       |
 1141|       |    // if we're in Class III, drop into the next finer Class II grid
 1142|  1.27k|    int res = H3_GET_RESOLUTION(h);
  ------------------
  |  |  129|  1.27k|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|  1.27k|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|  1.27k|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|  1.27k|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
 1143|  1.27k|    if (isResolutionClassIII(res)) {
  ------------------
  |  Branch (1143:9): [True: 1.08k, False: 189]
  ------------------
 1144|       |        // Class III
 1145|  1.08k|        _downAp7r(&fijk->coord);
 1146|  1.08k|        res++;
 1147|  1.08k|    }
 1148|       |
 1149|       |    // adjust for overage if needed
 1150|       |    // a pentagon base cell with a leading 4 digit requires special handling
 1151|  1.27k|    int pentLeading4 =
 1152|  1.27k|        (_isBaseCellPentagon(baseCell) && _h3LeadingNonZeroDigit(h) == 4);
  ------------------
  |  Branch (1152:10): [True: 672, False: 606]
  |  Branch (1152:43): [True: 195, False: 477]
  ------------------
 1153|  1.27k|    if (_adjustOverageClassII(fijk, res, pentLeading4, 0) != NO_OVERAGE) {
  ------------------
  |  Branch (1153:9): [True: 696, False: 582]
  ------------------
 1154|       |        // if the base cell is a pentagon we have the potential for secondary
 1155|       |        // overages
 1156|    696|        if (_isBaseCellPentagon(baseCell)) {
  ------------------
  |  Branch (1156:13): [True: 535, False: 161]
  ------------------
 1157|    917|            while (_adjustOverageClassII(fijk, res, 0, 0) != NO_OVERAGE)
  ------------------
  |  Branch (1157:20): [True: 382, False: 535]
  ------------------
 1158|    382|                continue;
 1159|    535|        }
 1160|       |
 1161|    696|        if (res != H3_GET_RESOLUTION(h)) _upAp7r(&fijk->coord);
  ------------------
  |  |  129|    696|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    696|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    696|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    696|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (1161:13): [True: 597, False: 99]
  ------------------
 1162|    696|    } else if (res != H3_GET_RESOLUTION(h)) {
  ------------------
  |  |  129|    582|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    582|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    582|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    582|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  |  Branch (1162:16): [True: 492, False: 90]
  ------------------
 1163|    492|        fijk->coord = origIJK;
 1164|    492|    }
 1165|  1.27k|    return E_SUCCESS;
 1166|  1.40k|}
maxFaceCount:
 1229|  1.26k|H3Error H3_EXPORT(maxFaceCount)(H3Index h3, int *out) {
 1230|       |    // a pentagon always intersects 5 faces, a hexagon never intersects more
 1231|       |    // than 2 (but may only intersect 1)
 1232|  1.26k|    *out = H3_EXPORT(isPentagon)(h3) ? 5 : 2;
  ------------------
  |  |   36|  1.26k|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|  1.26k|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|  1.26k|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (1232:12): [True: 40, False: 1.22k]
  ------------------
 1233|  1.26k|    return E_SUCCESS;
 1234|  1.26k|}
getIcosahedronFaces:
 1245|    646|H3Error H3_EXPORT(getIcosahedronFaces)(H3Index h3, int *out) {
 1246|    646|    int res = H3_GET_RESOLUTION(h3);
  ------------------
  |  |  129|    646|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    646|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    646|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    646|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
 1247|    646|    int isPent = H3_EXPORT(isPentagon)(h3);
  ------------------
  |  |   36|    646|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    646|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    646|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1248|       |
 1249|       |    // We can't use the vertex-based approach here for class II pentagons,
 1250|       |    // because all their vertices are on the icosahedron edges. Their
 1251|       |    // direct child pentagons cross the same faces, so use those instead.
 1252|    646|    if (isPent && !isResolutionClassIII(res)) {
  ------------------
  |  Branch (1252:9): [True: 34, False: 612]
  |  Branch (1252:19): [True: 14, False: 20]
  ------------------
 1253|       |        // Note that this would not work for res 15, but this is only run on
 1254|       |        // Class II pentagons, it should never be invoked for a res 15 index.
 1255|     14|        H3Index childPentagon = makeDirectChild(h3, 0);
 1256|     14|        return H3_EXPORT(getIcosahedronFaces)(childPentagon, out);
  ------------------
  |  |   36|     14|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|     14|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|     14|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1257|     14|    }
 1258|       |
 1259|       |    // convert to FaceIJK
 1260|    632|    FaceIJK fijk;
 1261|    632|    H3Error err = _h3ToFaceIjk(h3, &fijk);
 1262|    632|    if (err) {
  ------------------
  |  Branch (1262:9): [True: 3, False: 629]
  ------------------
 1263|      3|        return err;
 1264|      3|    }
 1265|       |
 1266|       |    // Get all vertices as FaceIJK addresses. For simplicity, always
 1267|       |    // initialize the array with 6 verts, ignoring the last one for pentagons
 1268|    629|    FaceIJK fijkVerts[NUM_HEX_VERTS];
 1269|    629|    int vertexCount;
 1270|       |
 1271|    629|    if (isPent) {
  ------------------
  |  Branch (1271:9): [True: 20, False: 609]
  ------------------
 1272|     20|        vertexCount = NUM_PENT_VERTS;
  ------------------
  |  |   85|     20|#define NUM_PENT_VERTS 5
  ------------------
 1273|     20|        _faceIjkPentToVerts(&fijk, &res, fijkVerts);
 1274|    609|    } else {
 1275|    609|        vertexCount = NUM_HEX_VERTS;
  ------------------
  |  |   83|    609|#define NUM_HEX_VERTS 6
  ------------------
 1276|    609|        _faceIjkToVerts(&fijk, &res, fijkVerts);
 1277|    609|    }
 1278|       |
 1279|       |    // We may not use all of the slots in the output array,
 1280|       |    // so fill with invalid values to indicate unused slots
 1281|    629|    int faceCount;
 1282|    629|    H3Error maxFaceCountError = H3_EXPORT(maxFaceCount)(h3, &faceCount);
  ------------------
  |  |   36|    629|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    629|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    629|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1283|    629|    if (NEVER(maxFaceCountError != E_SUCCESS)) {
  ------------------
  |  |  119|    629|#define NEVER(X) ((X) ? (assert(0), 1) : 0)
  |  |  ------------------
  |  |  |  Branch (119:18): [True: 0, False: 629]
  |  |  |  Branch (119:19): [True: 0, False: 629]
  |  |  ------------------
  ------------------
  |  Branch (1283:9): [Folded, False: 0]
  |  Branch (1283:9): [Folded, False: 0]
  ------------------
 1284|      0|        return maxFaceCountError;
 1285|      0|    }
 1286|  1.94k|    for (int i = 0; i < faceCount; i++) {
  ------------------
  |  Branch (1286:21): [True: 1.31k, False: 629]
  ------------------
 1287|  1.31k|        out[i] = INVALID_FACE;
  ------------------
  |  |   60|  1.31k|#define INVALID_FACE -1
  ------------------
 1288|  1.31k|    }
 1289|       |
 1290|       |    // add each vertex face, using the output array as a hash set
 1291|  4.37k|    for (int i = 0; i < vertexCount; i++) {
  ------------------
  |  Branch (1291:21): [True: 3.75k, False: 627]
  ------------------
 1292|  3.75k|        FaceIJK *vert = &fijkVerts[i];
 1293|       |
 1294|       |        // Adjust overage, determining whether this vertex is
 1295|       |        // on another face
 1296|  3.75k|        if (isPent) {
  ------------------
  |  Branch (1296:13): [True: 100, False: 3.65k]
  ------------------
 1297|    100|            _adjustPentVertOverage(vert, res);
 1298|  3.65k|        } else {
 1299|  3.65k|            _adjustOverageClassII(vert, res, 0, 1);
 1300|  3.65k|        }
 1301|       |
 1302|       |        // Save the face to the output array
 1303|  3.75k|        int face = vert->face;
 1304|  3.75k|        int pos = 0;
 1305|       |        // Find the first empty output position, or the first position
 1306|       |        // matching the current face
 1307|  4.05k|        while (out[pos] != INVALID_FACE && out[pos] != face) {
  ------------------
  |  |   60|  8.10k|#define INVALID_FACE -1
  ------------------
  |  Branch (1307:16): [True: 3.30k, False: 754]
  |  Branch (1307:44): [True: 305, False: 2.99k]
  ------------------
 1308|    305|            pos++;
 1309|    305|            if (pos >= faceCount) {
  ------------------
  |  Branch (1309:17): [True: 2, False: 303]
  ------------------
 1310|       |                // Mismatch between the heuristic used in maxFaceCount and
 1311|       |                // calculation here - indicates an invalid index.
 1312|      2|                return E_FAILED;
 1313|      2|            }
 1314|    305|        }
 1315|  3.74k|        out[pos] = face;
 1316|  3.74k|    }
 1317|    627|    return E_SUCCESS;
 1318|    629|}
isResolutionClassIII:
 1355|  21.2k|int isResolutionClassIII(int res) { return res % 2; }
h3Index.c:_hasGoodTopBits:
  216|  1.63k|static inline bool _hasGoodTopBits(H3Index h) {
  217|  1.63k|    h >>= (64 - 8);
  218|  1.63k|    return h == 0b00001000;
  219|  1.63k|}
h3Index.c:_hasAny7UptoRes:
  264|    621|static inline bool _hasAny7UptoRes(H3Index h, int res) {
  265|    621|    const uint64_t MHI = 0b100100100100100100100100100100100100100100100;
  266|    621|    const uint64_t MLO = MHI >> 2;
  267|       |
  268|    621|    int shift = 3 * (15 - res);
  269|    621|    h >>= shift;
  270|    621|    h <<= shift;
  271|    621|    h = (h & MHI & (~h - MLO));
  272|       |
  273|    621|    return h != 0;
  274|    621|}
h3Index.c:_hasAll7AfterRes:
  280|    548|static inline bool _hasAll7AfterRes(H3Index h, int res) {
  281|       |    // NOTE: res check is needed because we can't shift by 64
  282|    548|    if (res < 15) {
  ------------------
  |  Branch (282:9): [True: 263, False: 285]
  ------------------
  283|    263|        int shift = 19 + 3 * res;
  284|       |
  285|    263|        h = ~h;
  286|    263|        h <<= shift;
  287|    263|        h >>= shift;
  288|       |
  289|    263|        return h == 0;
  290|    263|    }
  291|    285|    return true;
  292|    548|}
h3Index.c:_hasDeletedSubsequence:
  327|    436|static inline bool _hasDeletedSubsequence(H3Index h, int base_cell) {
  328|    436|    if (isBaseCellPentagonArr[base_cell]) {
  ------------------
  |  Branch (328:9): [True: 256, False: 180]
  ------------------
  329|    256|        h <<= 19;
  330|    256|        h >>= 19;
  331|       |
  332|    256|        if (h == 0) return false;  // all zeros: res 15 pentagon
  ------------------
  |  Branch (332:13): [True: 5, False: 251]
  ------------------
  333|    251|        return _firstOneIndex(h) % 3 == 0;
  334|    256|    }
  335|    180|    return false;
  336|    436|}
h3Index.c:_firstOneIndex:
  300|    251|static inline int _firstOneIndex(H3Index h) {
  301|    251|#if defined(__GNUC__) || defined(__clang__)
  302|    251|    return 63 - __builtin_clzll(h);
  303|       |#elif defined(_MSC_VER) && defined(_M_X64)  // doesn't work on win32
  304|       |    unsigned long index;
  305|       |    _BitScanReverse64(&index, h);
  306|       |    return (int)index;
  307|       |#else
  308|       |    // Portable fallback
  309|       |    int pos = 63 - 19;
  310|       |    H3Index m = 1;
  311|       |    while ((h & (m << pos)) == 0) pos--;
  312|       |    return pos;
  313|       |#endif
  314|    251|}

vertexNumForDirection:
  130|    213|int vertexNumForDirection(const H3Index origin, const Direction direction) {
  131|    213|    int isPent = H3_EXPORT(isPentagon)(origin);
  ------------------
  |  |   36|    213|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    213|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    213|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  132|       |    // Check for invalid directions
  133|    213|    if (direction == CENTER_DIGIT || direction >= INVALID_DIGIT ||
  ------------------
  |  Branch (133:9): [True: 0, False: 213]
  |  Branch (133:38): [True: 0, False: 213]
  ------------------
  134|    213|        (isPent && direction == K_AXES_DIGIT))
  ------------------
  |  Branch (134:10): [True: 31, False: 182]
  |  Branch (134:20): [True: 0, False: 31]
  ------------------
  135|      0|        return INVALID_VERTEX_NUM;
  ------------------
  |  |   36|      0|#define INVALID_VERTEX_NUM -1
  ------------------
  136|       |
  137|       |    // Determine the vertex rotations for this cell
  138|    213|    int rotations;
  139|    213|    H3Error err = vertexRotations(origin, &rotations);
  140|    213|    if (err) {
  ------------------
  |  Branch (140:9): [True: 0, False: 213]
  ------------------
  141|      0|        return INVALID_VERTEX_NUM;
  ------------------
  |  |   36|      0|#define INVALID_VERTEX_NUM -1
  ------------------
  142|      0|    }
  143|       |
  144|       |    // Find the appropriate vertex, rotating CCW if necessary
  145|    213|    if (isPent) {
  ------------------
  |  Branch (145:9): [True: 31, False: 182]
  ------------------
  146|     31|        return (directionToVertexNumPent[direction] + NUM_PENT_VERTS -
  ------------------
  |  |   85|     31|#define NUM_PENT_VERTS 5
  ------------------
  147|     31|                rotations) %
  148|     31|               NUM_PENT_VERTS;
  ------------------
  |  |   85|     31|#define NUM_PENT_VERTS 5
  ------------------
  149|    182|    } else {
  150|    182|        return (directionToVertexNumHex[direction] + NUM_HEX_VERTS -
  ------------------
  |  |   83|    182|#define NUM_HEX_VERTS 6
  ------------------
  151|    182|                rotations) %
  152|    182|               NUM_HEX_VERTS;
  ------------------
  |  |   83|    182|#define NUM_HEX_VERTS 6
  ------------------
  153|    182|    }
  154|    213|}
directionForVertexNum:
  173|    565|Direction directionForVertexNum(const H3Index origin, const int vertexNum) {
  174|    565|    int isPent = H3_EXPORT(isPentagon)(origin);
  ------------------
  |  |   36|    565|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    565|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    565|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  175|       |    // Check for invalid vertexes
  176|    565|    if (vertexNum < 0 ||
  ------------------
  |  Branch (176:9): [True: 0, False: 565]
  ------------------
  177|    565|        vertexNum > (isPent ? NUM_PENT_VERTS : NUM_HEX_VERTS) - 1)
  ------------------
  |  |   85|      4|#define NUM_PENT_VERTS 5
  ------------------
                      vertexNum > (isPent ? NUM_PENT_VERTS : NUM_HEX_VERTS) - 1)
  ------------------
  |  |   83|    561|#define NUM_HEX_VERTS 6
  ------------------
  |  Branch (177:9): [True: 0, False: 565]
  |  Branch (177:22): [True: 4, False: 561]
  ------------------
  178|      0|        return INVALID_DIGIT;
  179|       |
  180|       |    // Determine the vertex rotations for this cell
  181|    565|    int rotations;
  182|    565|    H3Error err = vertexRotations(origin, &rotations);
  183|    565|    if (err) {
  ------------------
  |  Branch (183:9): [True: 0, False: 565]
  ------------------
  184|      0|        return INVALID_DIGIT;
  185|      0|    }
  186|       |
  187|       |    // Find the appropriate direction, rotating CW if necessary
  188|    565|    return isPent ? vertexNumToDirectionPent[(vertexNum + rotations) %
  ------------------
  |  Branch (188:12): [True: 4, False: 561]
  ------------------
  189|      4|                                             NUM_PENT_VERTS]
  ------------------
  |  |   85|      4|#define NUM_PENT_VERTS 5
  ------------------
  190|    565|                  : vertexNumToDirectionHex[(vertexNum + rotations) %
  191|    561|                                            NUM_HEX_VERTS];
  ------------------
  |  |   83|    561|#define NUM_HEX_VERTS 6
  ------------------
  192|    565|}
cellToVertex:
  212|    307|H3Error H3_EXPORT(cellToVertex)(H3Index cell, int vertexNum, H3Index *out) {
  213|    307|    int cellIsPentagon = H3_EXPORT(isPentagon)(cell);
  ------------------
  |  |   36|    307|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    307|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    307|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  214|    307|    int cellNumVerts = cellIsPentagon ? NUM_PENT_VERTS : NUM_HEX_VERTS;
  ------------------
  |  |   85|      4|#define NUM_PENT_VERTS 5
  ------------------
                  int cellNumVerts = cellIsPentagon ? NUM_PENT_VERTS : NUM_HEX_VERTS;
  ------------------
  |  |   83|    303|#define NUM_HEX_VERTS 6
  ------------------
  |  Branch (214:24): [True: 4, False: 303]
  ------------------
  215|    307|    int res = H3_GET_RESOLUTION(cell);
  ------------------
  |  |  129|    307|#define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   68|    307|#define H3_RES_MASK (UINT64_C(15) << H3_RES_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   41|    307|#define H3_RES_OFFSET 52
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_RESOLUTION(h3) ((int)((((h3)&H3_RES_MASK) >> H3_RES_OFFSET)))
  |  |  ------------------
  |  |  |  |   41|    307|#define H3_RES_OFFSET 52
  |  |  ------------------
  ------------------
  216|       |
  217|       |    // Check for invalid vertexes
  218|    307|    if (vertexNum < 0 || vertexNum > cellNumVerts - 1) return E_DOMAIN;
  ------------------
  |  Branch (218:9): [True: 0, False: 307]
  |  Branch (218:26): [True: 6, False: 301]
  ------------------
  219|       |
  220|       |    // Default the owner and vertex number to the input cell
  221|    301|    H3Index owner = cell;
  222|    301|    int ownerVertexNum = vertexNum;
  223|       |
  224|       |    // Determine the owner, looking at the three cells that share the vertex.
  225|       |    // By convention, the owner is the cell with the lowest numerical index.
  226|       |
  227|       |    // If the cell is the center child of its parent, it will always have
  228|       |    // the lowest index of any neighbor, so we can skip determining the owner
  229|    301|    if (res == 0 || H3_GET_INDEX_DIGIT(cell, res) != CENTER_DIGIT) {
  ------------------
  |  |  141|    287|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|    287|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|    287|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|    287|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|    287|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  |  Branch (229:9): [True: 14, False: 287]
  |  Branch (229:21): [True: 281, False: 6]
  ------------------
  230|       |        // Get the left neighbor of the vertex, with its rotations
  231|    295|        Direction left = directionForVertexNum(cell, vertexNum);
  232|    295|        if (left == INVALID_DIGIT) return E_FAILED;
  ------------------
  |  Branch (232:13): [True: 0, False: 295]
  ------------------
  233|    295|        int lRotations = 0;
  234|    295|        H3Index leftNeighbor;
  235|    295|        H3Error leftNeighborError =
  236|    295|            h3NeighborRotations(cell, left, &lRotations, &leftNeighbor);
  237|    295|        if (leftNeighborError) return leftNeighborError;
  ------------------
  |  Branch (237:13): [True: 0, False: 295]
  ------------------
  238|       |        // Set to owner if lowest index
  239|    295|        if (leftNeighbor < owner) owner = leftNeighbor;
  ------------------
  |  Branch (239:13): [True: 168, False: 127]
  ------------------
  240|       |
  241|       |        // As above, skip the right neighbor if the left is known lowest
  242|    295|        if (res == 0 || H3_GET_INDEX_DIGIT(leftNeighbor, res) != CENTER_DIGIT) {
  ------------------
  |  |  141|    281|    ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   76|    281|#define MAX_H3_RES 15
  |  |  ------------------
  |  |                   ((Direction)((((h3) >> ((MAX_H3_RES - (res)) * H3_PER_DIGIT_OFFSET)) & \
  |  |  ------------------
  |  |  |  |   47|    281|#define H3_PER_DIGIT_OFFSET 3
  |  |  ------------------
  |  |  142|    281|                  H3_DIGIT_MASK)))
  |  |  ------------------
  |  |  |  |   80|    281|#define H3_DIGIT_MASK ((uint64_t)(7))
  |  |  ------------------
  ------------------
  |  Branch (242:13): [True: 14, False: 281]
  |  Branch (242:25): [True: 256, False: 25]
  ------------------
  243|       |            // Get the right neighbor of the vertex, with its rotations
  244|       |            // Note that vertex - 1 is the right side, as vertex numbers are CCW
  245|    270|            Direction right = directionForVertexNum(
  246|    270|                cell, (vertexNum - 1 + cellNumVerts) % cellNumVerts);
  247|       |            // This case should be unreachable; invalid verts fail earlier
  248|    270|            if (NEVER(right == INVALID_DIGIT)) return E_FAILED;
  ------------------
  |  |  119|    270|#define NEVER(X) ((X) ? (assert(0), 1) : 0)
  |  |  ------------------
  |  |  |  Branch (119:18): [True: 0, False: 270]
  |  |  |  Branch (119:19): [True: 0, False: 270]
  |  |  ------------------
  ------------------
  |  Branch (248:17): [Folded, False: 0]
  |  Branch (248:17): [Folded, False: 0]
  ------------------
  249|    270|            int rRotations = 0;
  250|    270|            H3Index rightNeighbor;
  251|    270|            H3Error rightNeighborError =
  252|    270|                h3NeighborRotations(cell, right, &rRotations, &rightNeighbor);
  253|    270|            if (rightNeighborError) return rightNeighborError;
  ------------------
  |  Branch (253:17): [True: 0, False: 270]
  ------------------
  254|       |            // Set to owner if lowest index
  255|    270|            if (rightNeighbor < owner) {
  ------------------
  |  Branch (255:17): [True: 108, False: 162]
  ------------------
  256|    108|                owner = rightNeighbor;
  257|    108|                Direction dir =
  258|    108|                    H3_EXPORT(isPentagon)(owner)
  ------------------
  |  |   36|    108|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    108|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    108|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (258:21): [True: 23, False: 85]
  ------------------
  259|    108|                        ? directionForNeighbor(owner, cell)
  260|    108|                        : DIRECTIONS[(revNeighborDirectionsHex[right] +
  261|     85|                                      rRotations) %
  262|     85|                                     NUM_HEX_VERTS];
  ------------------
  |  |   83|     85|#define NUM_HEX_VERTS 6
  ------------------
  263|    108|                ownerVertexNum = vertexNumForDirection(owner, dir);
  264|    108|            }
  265|    270|        }
  266|       |
  267|       |        // Determine the vertex number for the left neighbor
  268|    295|        if (owner == leftNeighbor) {
  ------------------
  |  Branch (268:13): [True: 105, False: 190]
  ------------------
  269|    105|            int ownerIsPentagon = H3_EXPORT(isPentagon)(owner);
  ------------------
  |  |   36|    105|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    105|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    105|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  270|    105|            Direction dir =
  271|    105|                ownerIsPentagon
  ------------------
  |  Branch (271:17): [True: 8, False: 97]
  ------------------
  272|    105|                    ? directionForNeighbor(owner, cell)
  273|    105|                    : DIRECTIONS[(revNeighborDirectionsHex[left] + lRotations) %
  274|     97|                                 NUM_HEX_VERTS];
  ------------------
  |  |   83|     97|#define NUM_HEX_VERTS 6
  ------------------
  275|       |
  276|       |            // For the left neighbor, we need the second vertex of the
  277|       |            // edge, which may involve looping around the vertex nums
  278|    105|            ownerVertexNum = vertexNumForDirection(owner, dir) + 1;
  279|    105|            if (ownerVertexNum == NUM_HEX_VERTS ||
  ------------------
  |  |   83|    210|#define NUM_HEX_VERTS 6
  ------------------
  |  Branch (279:17): [True: 8, False: 97]
  ------------------
  280|     97|                (ownerIsPentagon && ownerVertexNum == NUM_PENT_VERTS)) {
  ------------------
  |  |   85|      8|#define NUM_PENT_VERTS 5
  ------------------
  |  Branch (280:18): [True: 8, False: 89]
  |  Branch (280:37): [True: 2, False: 6]
  ------------------
  281|     10|                ownerVertexNum = 0;
  282|     10|            }
  283|    105|        }
  284|    295|    }
  285|       |
  286|       |    // Create the vertex index
  287|    301|    H3Index vertex = owner;
  288|    301|    H3_SET_MODE(vertex, H3_VERTEX_MODE);
  ------------------
  |  |  113|    301|    (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   59|    301|#define H3_MODE_MASK_NEGATIVE (~H3_MODE_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   56|    301|#define H3_MODE_MASK ((uint64_t)(15) << H3_MODE_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   35|    301|#define H3_MODE_OFFSET 59
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   35|    301|#define H3_MODE_OFFSET 59
  |  |  ------------------
  ------------------
  289|    301|    H3_SET_RESERVED_BITS(vertex, ownerVertexNum);
  ------------------
  |  |  149|    301|    (h3) = (((h3)&H3_RESERVED_MASK_NEGATIVE) | \
  |  |  ------------------
  |  |  |  |   77|    301|#define H3_RESERVED_MASK_NEGATIVE (~H3_RESERVED_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   74|    301|#define H3_RESERVED_MASK ((uint64_t)(7) << H3_RESERVED_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   44|    301|#define H3_RESERVED_OFFSET 56
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  150|    301|            (((uint64_t)(v)) << H3_RESERVED_OFFSET))
  |  |  ------------------
  |  |  |  |   44|    301|#define H3_RESERVED_OFFSET 56
  |  |  ------------------
  ------------------
  290|    301|    *out = vertex;
  291|       |
  292|    301|    return E_SUCCESS;
  293|    301|}
isValidVertex:
  354|    581|int H3_EXPORT(isValidVertex)(H3Index vertex) {
  355|    581|    if (H3_GET_MODE(vertex) != H3_VERTEX_MODE) {
  ------------------
  |  |  107|    581|#define H3_GET_MODE(h3) ((int)((((h3)&H3_MODE_MASK) >> H3_MODE_OFFSET)))
  |  |  ------------------
  |  |  |  |   56|    581|#define H3_MODE_MASK ((uint64_t)(15) << H3_MODE_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   35|    581|#define H3_MODE_OFFSET 59
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define H3_GET_MODE(h3) ((int)((((h3)&H3_MODE_MASK) >> H3_MODE_OFFSET)))
  |  |  ------------------
  |  |  |  |   35|    581|#define H3_MODE_OFFSET 59
  |  |  ------------------
  ------------------
                  if (H3_GET_MODE(vertex) != H3_VERTEX_MODE) {
  ------------------
  |  |   93|    581|#define H3_VERTEX_MODE 4
  ------------------
  |  Branch (355:9): [True: 227, False: 354]
  ------------------
  356|    227|        return 0;
  357|    227|    }
  358|       |
  359|    354|    int vertexNum = H3_GET_RESERVED_BITS(vertex);
  ------------------
  |  |  156|    354|    ((int)((((h3)&H3_RESERVED_MASK) >> H3_RESERVED_OFFSET)))
  |  |  ------------------
  |  |  |  |   74|    354|#define H3_RESERVED_MASK ((uint64_t)(7) << H3_RESERVED_OFFSET)
  |  |  |  |  ------------------
  |  |  |  |  |  |   44|    354|#define H3_RESERVED_OFFSET 56
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   ((int)((((h3)&H3_RESERVED_MASK) >> H3_RESERVED_OFFSET)))
  |  |  ------------------
  |  |  |  |   44|    354|#define H3_RESERVED_OFFSET 56
  |  |  ------------------
  ------------------
  360|    354|    H3Index owner = vertex;
  361|    354|    H3_SET_MODE(owner, H3_CELL_MODE);
  ------------------
  |  |  113|    354|    (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   59|    354|#define H3_MODE_MASK_NEGATIVE (~H3_MODE_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   56|    354|#define H3_MODE_MASK ((uint64_t)(15) << H3_MODE_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   35|    354|#define H3_MODE_OFFSET 59
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |                   (h3) = (((h3)&H3_MODE_MASK_NEGATIVE) | (((uint64_t)(v)) << H3_MODE_OFFSET))
  |  |  ------------------
  |  |  |  |   35|    354|#define H3_MODE_OFFSET 59
  |  |  ------------------
  ------------------
  362|    354|    H3_SET_RESERVED_BITS(owner, 0);
  ------------------
  |  |  149|    354|    (h3) = (((h3)&H3_RESERVED_MASK_NEGATIVE) | \
  |  |  ------------------
  |  |  |  |   77|    354|#define H3_RESERVED_MASK_NEGATIVE (~H3_RESERVED_MASK)
  |  |  |  |  ------------------
  |  |  |  |  |  |   74|    354|#define H3_RESERVED_MASK ((uint64_t)(7) << H3_RESERVED_OFFSET)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |   44|    354|#define H3_RESERVED_OFFSET 56
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  150|    354|            (((uint64_t)(v)) << H3_RESERVED_OFFSET))
  |  |  ------------------
  |  |  |  |   44|    354|#define H3_RESERVED_OFFSET 56
  |  |  ------------------
  ------------------
  363|       |
  364|    354|    if (!H3_EXPORT(isValidCell)(owner)) {
  ------------------
  |  |   36|    354|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    354|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    354|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (364:9): [True: 47, False: 307]
  ------------------
  365|     47|        return 0;
  366|     47|    }
  367|       |
  368|       |    // The easiest way to ensure that the owner + vertex number is valid,
  369|       |    // and that the vertex is canonical, is to recreate and compare.
  370|    307|    H3Index canonical;
  371|    307|    if (H3_EXPORT(cellToVertex)(owner, vertexNum, &canonical)) {
  ------------------
  |  |   36|    307|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    307|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    307|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  |  Branch (371:9): [True: 6, False: 301]
  ------------------
  372|      6|        return 0;
  373|      6|    }
  374|       |
  375|    301|    return vertex == canonical ? 1 : 0;
  ------------------
  |  Branch (375:12): [True: 88, False: 213]
  ------------------
  376|    307|}
vertex.c:vertexRotations:
   53|    778|static H3Error vertexRotations(H3Index cell, int *out) {
   54|       |    // Get the face and other info for the origin
   55|    778|    FaceIJK fijk;
   56|    778|    H3Error err = _h3ToFaceIjk(cell, &fijk);
   57|    778|    if (err) {
  ------------------
  |  Branch (57:9): [True: 0, False: 778]
  ------------------
   58|      0|        return err;
   59|      0|    }
   60|    778|    int baseCell = H3_EXPORT(getBaseCellNumber)(cell);
  ------------------
  |  |   36|    778|#define H3_EXPORT(name) TJOIN(H3_PREFIX, name)
  |  |  ------------------
  |  |  |  |   33|    778|#define TJOIN(a, b) XTJOIN(a, b)
  |  |  |  |  ------------------
  |  |  |  |  |  |   32|    778|#define XTJOIN(a, b) a##b
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
   61|    778|    int cellLeadingDigit = _h3LeadingNonZeroDigit(cell);
   62|       |
   63|       |    // get the base cell face
   64|    778|    FaceIJK baseFijk;
   65|    778|    _baseCellToFaceIjk(baseCell, &baseFijk);
   66|       |
   67|    778|    int ccwRot60 = _baseCellToCCWrot60(baseCell, fijk.face);
   68|       |
   69|    778|    if (_isBaseCellPentagon(baseCell)) {
  ------------------
  |  Branch (69:9): [True: 368, False: 410]
  ------------------
   70|       |        // Find the appropriate direction-to-face mapping
   71|    368|        PentagonDirectionFaces dirFaces;
   72|       |        // We never hit the end condition
   73|    368|        int p = 0;
   74|       |        // Don't use a for loop here, for coverage reasons.
   75|  2.58k|        while (ALWAYS(p < NUM_PENTAGONS)) {
  ------------------
  |  |  118|  2.58k|#define ALWAYS(X) ((X) ? 1 : (assert(0), 0))
  |  |  ------------------
  |  |  |  Branch (118:19): [True: 2.58k, False: 0]
  |  |  |  Branch (118:20): [True: 2.58k, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (75:16): [Folded, False: 0]
  |  Branch (75:16): [Folded, False: 0]
  ------------------
   76|  2.58k|            if (pentagonDirectionFaces[p].baseCell == baseCell) {
  ------------------
  |  Branch (76:17): [True: 368, False: 2.21k]
  ------------------
   77|    368|                dirFaces = pentagonDirectionFaces[p];
   78|    368|                break;
   79|    368|            }
   80|  2.21k|            p++;
   81|  2.21k|        }
   82|    368|        if (NEVER(p == NUM_PENTAGONS)) {
  ------------------
  |  |  119|    368|#define NEVER(X) ((X) ? (assert(0), 1) : 0)
  |  |  ------------------
  |  |  |  Branch (119:18): [True: 0, False: 368]
  |  |  |  Branch (119:19): [True: 0, False: 368]
  |  |  ------------------
  ------------------
  |  Branch (82:13): [Folded, False: 0]
  |  Branch (82:13): [Folded, False: 0]
  ------------------
   83|      0|            return E_FAILED;
   84|      0|        }
   85|       |
   86|       |        // additional CCW rotation for polar neighbors or IK neighbors
   87|    368|        if (fijk.face != baseFijk.face &&
  ------------------
  |  Branch (87:13): [True: 278, False: 90]
  ------------------
   88|    278|            (_isBaseCellPolarPentagon(baseCell) ||
  ------------------
  |  Branch (88:14): [True: 101, False: 177]
  ------------------
   89|    177|             fijk.face ==
  ------------------
  |  Branch (89:14): [True: 80, False: 97]
  ------------------
   90|    181|                 dirFaces.faces[IK_AXES_DIGIT - DIRECTION_INDEX_OFFSET])) {
  ------------------
  |  |   32|    177|#define DIRECTION_INDEX_OFFSET 2
  ------------------
   91|    181|            ccwRot60 = (ccwRot60 + 1) % 6;
   92|    181|        }
   93|       |
   94|       |        // Check whether the cell crosses a deleted pentagon subsequence
   95|    368|        if (cellLeadingDigit == JK_AXES_DIGIT &&
  ------------------
  |  Branch (95:13): [True: 68, False: 300]
  ------------------
   96|     68|            fijk.face ==
  ------------------
  |  Branch (96:13): [True: 28, False: 40]
  ------------------
   97|     68|                dirFaces.faces[IK_AXES_DIGIT - DIRECTION_INDEX_OFFSET]) {
  ------------------
  |  |   32|     68|#define DIRECTION_INDEX_OFFSET 2
  ------------------
   98|       |            // Crosses from JK to IK: Rotate CW
   99|     28|            ccwRot60 = (ccwRot60 + 5) % 6;
  100|    340|        } else if (cellLeadingDigit == IK_AXES_DIGIT &&
  ------------------
  |  Branch (100:20): [True: 95, False: 245]
  ------------------
  101|     95|                   fijk.face ==
  ------------------
  |  Branch (101:20): [True: 11, False: 84]
  ------------------
  102|     95|                       dirFaces.faces[JK_AXES_DIGIT - DIRECTION_INDEX_OFFSET]) {
  ------------------
  |  |   32|     95|#define DIRECTION_INDEX_OFFSET 2
  ------------------
  103|       |            // Crosses from IK to JK: Rotate CCW
  104|     11|            ccwRot60 = (ccwRot60 + 1) % 6;
  105|     11|        }
  106|    368|    }
  107|    778|    *out = ccwRot60;
  108|    778|    return E_SUCCESS;
  109|    778|}

