size_t git_path_basename_offset(git_buf *buffer) { ssize_t slash; if (!buffer || buffer->size <= 0) return 0; slash = git_buf_rfind_next(buffer, '/'); if (slash >= 0 && buffer->ptr[slash] == '/') return (size_t)(slash + 1); return 0; }
void test_core_buffer__rfind_variants(void) { git_buf a = GIT_BUF_INIT; ssize_t len; cl_git_pass(git_buf_sets(&a, "/this/is/it/")); len = (ssize_t)git_buf_len(&a); cl_assert(git_buf_rfind(&a, '/') == len - 1); cl_assert(git_buf_rfind_next(&a, '/') == len - 4); cl_assert(git_buf_rfind(&a, 'i') == len - 3); cl_assert(git_buf_rfind_next(&a, 'i') == len - 3); cl_assert(git_buf_rfind(&a, 'h') == 2); cl_assert(git_buf_rfind_next(&a, 'h') == 2); cl_assert(git_buf_rfind(&a, 'q') == -1); cl_assert(git_buf_rfind_next(&a, 'q') == -1); git_buf_free(&a); }
int git_path_walk_up( git_buf *path, const char *ceiling, int (*cb)(void *data, git_buf *), void *data) { int error = 0; git_buf iter; ssize_t stop = 0, scan; char oldc = '\0'; assert(path && cb); if (ceiling != NULL) { if (git__prefixcmp(path->ptr, ceiling) == 0) stop = (ssize_t)strlen(ceiling); else stop = git_buf_len(path); } scan = git_buf_len(path); iter.ptr = path->ptr; iter.size = git_buf_len(path); iter.asize = path->asize; while (scan >= stop) { error = cb(data, &iter); iter.ptr[scan] = oldc; if (error) { giterr_set_after_callback(error); break; } scan = git_buf_rfind_next(&iter, '/'); if (scan >= 0) { scan++; oldc = iter.ptr[scan]; iter.size = scan; iter.ptr[scan] = '\0'; } } if (scan >= 0) iter.ptr[scan] = oldc; return error; }
int git_path_walk_up( git_buf *path, const char *ceiling, int (*cb)(void *data, git_buf *), void *data) { int error = GIT_SUCCESS; git_buf iter; ssize_t stop = 0, scan; char oldc = '\0'; assert(path && cb); if (ceiling != NULL) { if (git__prefixcmp(path->ptr, ceiling) == GIT_SUCCESS) stop = (ssize_t)strlen(ceiling); else stop = path->size; } scan = path->size; iter.ptr = path->ptr; iter.size = path->size; iter.asize = path->asize; while (scan >= stop) { if ((error = cb(data, &iter)) < GIT_SUCCESS) break; iter.ptr[scan] = oldc; scan = git_buf_rfind_next(&iter, '/'); if (scan >= 0) { scan++; oldc = iter.ptr[scan]; iter.size = scan; iter.ptr[scan] = '\0'; } } if (scan >= 0) iter.ptr[scan] = oldc; return error; }
int git_path_walk_up( git_buf *path, const char *ceiling, int (*cb)(void *data, const char *), void *data) { int error = 0; git_buf iter; ssize_t stop = 0, scan; char oldc = '\0'; assert(path && cb); if (ceiling != NULL) { if (git__prefixcmp(path->ptr, ceiling) == 0) stop = (ssize_t)strlen(ceiling); else stop = git_buf_len(path); } scan = git_buf_len(path); /* empty path: yield only once */ if (!scan) { error = cb(data, ""); if (error) giterr_set_after_callback(error); return error; } iter.ptr = path->ptr; iter.size = git_buf_len(path); iter.asize = path->asize; while (scan >= stop) { error = cb(data, iter.ptr); iter.ptr[scan] = oldc; if (error) { giterr_set_after_callback(error); break; } scan = git_buf_rfind_next(&iter, '/'); if (scan >= 0) { scan++; oldc = iter.ptr[scan]; iter.size = scan; iter.ptr[scan] = '\0'; } } if (scan >= 0) iter.ptr[scan] = oldc; /* relative path: yield for the last component */ if (!error && stop == 0 && iter.ptr[0] != '/') { error = cb(data, ""); if (error) giterr_set_after_callback(error); } return error; }