rugged 1.3.2 → 1.6.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +34 -2
- data/ext/rugged/extconf.rb +7 -4
- data/ext/rugged/rugged.c +16 -0
- data/ext/rugged/rugged.h +4 -0
- data/ext/rugged/rugged_blame.c +2 -0
- data/ext/rugged/rugged_blob.c +3 -0
- data/ext/rugged/rugged_commit.c +1 -0
- data/ext/rugged/rugged_config.c +9 -2
- data/ext/rugged/rugged_diff.c +1 -0
- data/ext/rugged/rugged_index.c +2 -0
- data/ext/rugged/rugged_patch.c +1 -0
- data/ext/rugged/rugged_rebase.c +1 -0
- data/ext/rugged/rugged_reference.c +1 -0
- data/ext/rugged/rugged_remote.c +28 -10
- data/ext/rugged/rugged_repo.c +7 -9
- data/ext/rugged/rugged_revwalk.c +5 -1
- data/ext/rugged/rugged_settings.c +5 -0
- data/ext/rugged/rugged_submodule.c +1 -0
- data/ext/rugged/rugged_tag.c +1 -0
- data/ext/rugged/rugged_tree.c +4 -0
- data/lib/rugged/index.rb +1 -1
- data/lib/rugged/tree.rb +5 -1
- data/lib/rugged/version.rb +1 -1
- data/vendor/libgit2/CMakeLists.txt +132 -288
- data/vendor/libgit2/COPYING +106 -19
- data/vendor/libgit2/cmake/AddCFlagIfSupported.cmake +21 -21
- data/vendor/libgit2/cmake/AddClarTest.cmake +7 -0
- data/vendor/libgit2/cmake/DefaultCFlags.cmake +154 -0
- data/vendor/libgit2/cmake/EnableWarnings.cmake +13 -13
- data/vendor/libgit2/cmake/ExperimentalFeatures.cmake +23 -0
- data/vendor/libgit2/cmake/FindCoreFoundation.cmake +13 -13
- data/vendor/libgit2/cmake/FindGSSAPI.cmake +171 -287
- data/vendor/libgit2/cmake/FindGSSFramework.cmake +13 -13
- data/vendor/libgit2/cmake/{FindHTTP_Parser.cmake → FindHTTPParser.cmake} +17 -17
- data/vendor/libgit2/cmake/FindIconv.cmake +27 -27
- data/vendor/libgit2/cmake/FindLibSSH2.cmake +5 -5
- data/vendor/libgit2/cmake/FindPCRE.cmake +12 -13
- data/vendor/libgit2/cmake/FindPCRE2.cmake +12 -12
- data/vendor/libgit2/cmake/FindPkgLibraries.cmake +19 -19
- data/vendor/libgit2/cmake/FindSecurity.cmake +14 -14
- data/vendor/libgit2/cmake/FindStatNsec.cmake +12 -18
- data/vendor/libgit2/cmake/Findfutimens.cmake +8 -8
- data/vendor/libgit2/cmake/FindmbedTLS.cmake +63 -70
- data/vendor/libgit2/cmake/IdeSplitSources.cmake +18 -18
- data/vendor/libgit2/cmake/PkgBuildConfig.cmake +60 -60
- data/vendor/libgit2/cmake/SanitizeBool.cmake +20 -20
- data/vendor/libgit2/cmake/SelectGSSAPI.cmake +37 -37
- data/vendor/libgit2/cmake/SelectHTTPParser.cmake +19 -0
- data/vendor/libgit2/cmake/SelectHTTPSBackend.cmake +100 -100
- data/vendor/libgit2/cmake/SelectHashes.cmake +91 -53
- data/vendor/libgit2/cmake/SelectRegex.cmake +51 -0
- data/vendor/libgit2/cmake/SelectSSH.cmake +41 -0
- data/vendor/libgit2/cmake/SelectWinHTTP.cmake +17 -0
- data/vendor/libgit2/cmake/SelectZlib.cmake +34 -0
- data/vendor/libgit2/deps/chromium-zlib/CMakeLists.txt +6 -6
- data/vendor/libgit2/deps/ntlmclient/CMakeLists.txt +33 -31
- data/vendor/libgit2/deps/ntlmclient/crypt_openssl.c +3 -1
- data/vendor/libgit2/deps/ntlmclient/ntlm.c +4 -4
- data/vendor/libgit2/deps/ntlmclient/ntlm.h +4 -4
- data/vendor/libgit2/deps/ntlmclient/ntlmclient.h +2 -2
- data/vendor/libgit2/deps/pcre/CMakeLists.txt +88 -88
- data/vendor/libgit2/deps/winhttp/CMakeLists.txt +14 -16
- data/vendor/libgit2/deps/zlib/adler32.c +7 -0
- data/vendor/libgit2/deps/zlib/crc32.c +975 -288
- data/vendor/libgit2/deps/zlib/crc32.h +9441 -436
- data/vendor/libgit2/deps/zlib/deflate.c +83 -31
- data/vendor/libgit2/deps/zlib/deflate.h +12 -15
- data/vendor/libgit2/deps/zlib/gzguts.h +3 -2
- data/vendor/libgit2/deps/zlib/infback.c +2 -1
- data/vendor/libgit2/deps/zlib/inffast.c +14 -14
- data/vendor/libgit2/deps/zlib/inflate.c +39 -8
- data/vendor/libgit2/deps/zlib/inflate.h +3 -2
- data/vendor/libgit2/deps/zlib/inftrees.c +3 -3
- data/vendor/libgit2/deps/zlib/trees.c +27 -48
- data/vendor/libgit2/deps/zlib/zlib.h +126 -100
- data/vendor/libgit2/deps/zlib/zutil.c +2 -2
- data/vendor/libgit2/deps/zlib/zutil.h +12 -9
- data/vendor/libgit2/include/git2/apply.h +16 -2
- data/vendor/libgit2/include/git2/attr.h +11 -2
- data/vendor/libgit2/include/git2/blame.h +4 -1
- data/vendor/libgit2/include/git2/blob.h +14 -1
- data/vendor/libgit2/include/git2/branch.h +4 -2
- data/vendor/libgit2/include/git2/buffer.h +18 -78
- data/vendor/libgit2/include/git2/cert.h +2 -2
- data/vendor/libgit2/include/git2/checkout.h +5 -2
- data/vendor/libgit2/include/git2/clone.h +3 -3
- data/vendor/libgit2/include/git2/commit.h +2 -0
- data/vendor/libgit2/include/git2/common.h +28 -7
- data/vendor/libgit2/include/git2/config.h +25 -9
- data/vendor/libgit2/include/git2/credential.h +2 -1
- data/vendor/libgit2/include/git2/credential_helpers.h +1 -0
- data/vendor/libgit2/include/git2/deprecated.h +9 -1
- data/vendor/libgit2/include/git2/describe.h +7 -2
- data/vendor/libgit2/include/git2/diff.h +18 -10
- data/vendor/libgit2/include/git2/email.h +1 -1
- data/vendor/libgit2/include/git2/errors.h +17 -3
- data/vendor/libgit2/include/git2/experimental.h +20 -0
- data/vendor/libgit2/include/git2/filter.h +7 -2
- data/vendor/libgit2/include/git2/graph.h +1 -0
- data/vendor/libgit2/include/git2/ignore.h +1 -1
- data/vendor/libgit2/include/git2/index.h +11 -5
- data/vendor/libgit2/include/git2/indexer.h +48 -0
- data/vendor/libgit2/include/git2/merge.h +24 -4
- data/vendor/libgit2/include/git2/message.h +2 -0
- data/vendor/libgit2/include/git2/object.h +49 -0
- data/vendor/libgit2/include/git2/odb.h +94 -13
- data/vendor/libgit2/include/git2/odb_backend.h +107 -19
- data/vendor/libgit2/include/git2/oid.h +115 -15
- data/vendor/libgit2/include/git2/pack.h +24 -8
- data/vendor/libgit2/include/git2/patch.h +8 -0
- data/vendor/libgit2/include/git2/pathspec.h +1 -1
- data/vendor/libgit2/include/git2/proxy.h +1 -1
- data/vendor/libgit2/include/git2/rebase.h +9 -1
- data/vendor/libgit2/include/git2/refdb.h +3 -0
- data/vendor/libgit2/include/git2/reflog.h +1 -1
- data/vendor/libgit2/include/git2/refs.h +2 -2
- data/vendor/libgit2/include/git2/remote.h +184 -37
- data/vendor/libgit2/include/git2/repository.h +34 -10
- data/vendor/libgit2/include/git2/reset.h +2 -2
- data/vendor/libgit2/include/git2/revparse.h +1 -1
- data/vendor/libgit2/include/git2/revwalk.h +4 -1
- data/vendor/libgit2/include/git2/signature.h +1 -1
- data/vendor/libgit2/include/git2/stash.h +61 -7
- data/vendor/libgit2/include/git2/status.h +14 -5
- data/vendor/libgit2/include/git2/strarray.h +0 -13
- data/vendor/libgit2/include/git2/submodule.h +7 -2
- data/vendor/libgit2/include/git2/sys/commit_graph.h +1 -1
- data/vendor/libgit2/include/git2/sys/odb_backend.h +3 -6
- data/vendor/libgit2/include/git2/sys/remote.h +46 -0
- data/vendor/libgit2/include/git2/sys/stream.h +1 -1
- data/vendor/libgit2/include/git2/sys/transport.h +46 -39
- data/vendor/libgit2/include/git2/tag.h +1 -0
- data/vendor/libgit2/include/git2/tree.h +4 -3
- data/vendor/libgit2/include/git2/types.h +7 -7
- data/vendor/libgit2/include/git2/version.h +27 -6
- data/vendor/libgit2/include/git2/worktree.h +12 -2
- data/vendor/libgit2/include/git2.h +1 -0
- data/vendor/libgit2/src/CMakeLists.txt +177 -419
- data/vendor/libgit2/src/README.md +12 -0
- data/vendor/libgit2/src/cli/CMakeLists.txt +57 -0
- data/vendor/libgit2/src/cli/README.md +26 -0
- data/vendor/libgit2/src/cli/cli.h +20 -0
- data/vendor/libgit2/src/cli/cmd.c +21 -0
- data/vendor/libgit2/src/cli/cmd.h +33 -0
- data/vendor/libgit2/src/cli/cmd_cat_file.c +204 -0
- data/vendor/libgit2/src/cli/cmd_clone.c +176 -0
- data/vendor/libgit2/src/cli/cmd_hash_object.c +154 -0
- data/vendor/libgit2/src/cli/cmd_help.c +86 -0
- data/vendor/libgit2/src/cli/error.h +51 -0
- data/vendor/libgit2/src/cli/main.c +106 -0
- data/vendor/libgit2/src/cli/opt.c +669 -0
- data/vendor/libgit2/src/cli/opt.h +349 -0
- data/vendor/libgit2/src/cli/opt_usage.c +194 -0
- data/vendor/libgit2/src/cli/opt_usage.h +35 -0
- data/vendor/libgit2/src/cli/progress.c +345 -0
- data/vendor/libgit2/src/cli/progress.h +117 -0
- data/vendor/libgit2/src/cli/sighandler.h +20 -0
- data/vendor/libgit2/src/cli/unix/sighandler.c +36 -0
- data/vendor/libgit2/src/cli/win32/precompiled.h +3 -0
- data/vendor/libgit2/src/cli/win32/sighandler.c +37 -0
- data/vendor/libgit2/src/libgit2/CMakeLists.txt +141 -0
- data/vendor/libgit2/src/{annotated_commit.c → libgit2/annotated_commit.c} +1 -1
- data/vendor/libgit2/src/{annotated_commit.h → libgit2/annotated_commit.h} +2 -2
- data/vendor/libgit2/src/{apply.c → libgit2/apply.c} +18 -18
- data/vendor/libgit2/src/{apply.h → libgit2/apply.h} +2 -2
- data/vendor/libgit2/src/{attr.c → libgit2/attr.c} +18 -18
- data/vendor/libgit2/src/{attr_file.c → libgit2/attr_file.c} +18 -18
- data/vendor/libgit2/src/{attr_file.h → libgit2/attr_file.h} +4 -4
- data/vendor/libgit2/src/{attrcache.c → libgit2/attrcache.c} +18 -13
- data/vendor/libgit2/src/{blame.c → libgit2/blame.c} +2 -0
- data/vendor/libgit2/src/{blame_git.c → libgit2/blame_git.c} +1 -1
- data/vendor/libgit2/src/{blob.c → libgit2/blob.c} +38 -29
- data/vendor/libgit2/src/{blob.h → libgit2/blob.h} +3 -3
- data/vendor/libgit2/src/{branch.c → libgit2/branch.c} +164 -118
- data/vendor/libgit2/src/{branch.h → libgit2/branch.h} +15 -3
- data/vendor/libgit2/src/libgit2/buf.c +126 -0
- data/vendor/libgit2/src/libgit2/buf.h +50 -0
- data/vendor/libgit2/src/{checkout.c → libgit2/checkout.c} +74 -68
- data/vendor/libgit2/src/{cherrypick.c → libgit2/cherrypick.c} +13 -13
- data/vendor/libgit2/src/{clone.c → libgit2/clone.c} +96 -67
- data/vendor/libgit2/src/{commit.c → libgit2/commit.c} +178 -73
- data/vendor/libgit2/src/libgit2/commit.h +87 -0
- data/vendor/libgit2/src/{commit_graph.c → libgit2/commit_graph.c} +122 -89
- data/vendor/libgit2/src/{commit_graph.h → libgit2/commit_graph.h} +14 -4
- data/vendor/libgit2/src/{commit_list.c → libgit2/commit_list.c} +7 -4
- data/vendor/libgit2/src/libgit2/common.h +55 -0
- data/vendor/libgit2/src/{config.c → libgit2/config.c} +101 -69
- data/vendor/libgit2/src/{config.h → libgit2/config.h} +15 -2
- data/vendor/libgit2/src/{config_file.c → libgit2/config_file.c} +105 -93
- data/vendor/libgit2/src/{config_mem.c → libgit2/config_mem.c} +9 -9
- data/vendor/libgit2/src/{config_parse.c → libgit2/config_parse.c} +27 -23
- data/vendor/libgit2/src/{crlf.c → libgit2/crlf.c} +24 -21
- data/vendor/libgit2/src/{describe.c → libgit2/describe.c} +35 -27
- data/vendor/libgit2/src/{diff.c → libgit2/diff.c} +30 -9
- data/vendor/libgit2/src/{diff.h → libgit2/diff.h} +2 -4
- data/vendor/libgit2/src/{diff_driver.c → libgit2/diff_driver.c} +34 -36
- data/vendor/libgit2/src/{diff_driver.h → libgit2/diff_driver.h} +3 -3
- data/vendor/libgit2/src/{diff_file.c → libgit2/diff_file.c} +44 -26
- data/vendor/libgit2/src/{diff_generate.c → libgit2/diff_generate.c} +47 -18
- data/vendor/libgit2/src/{diff_generate.h → libgit2/diff_generate.h} +5 -3
- data/vendor/libgit2/src/{diff_print.c → libgit2/diff_print.c} +112 -100
- data/vendor/libgit2/src/{diff_stats.c → libgit2/diff_stats.c} +40 -29
- data/vendor/libgit2/src/libgit2/diff_stats.h +18 -0
- data/vendor/libgit2/src/{diff_tform.c → libgit2/diff_tform.c} +13 -8
- data/vendor/libgit2/src/{diff_xdiff.c → libgit2/diff_xdiff.c} +4 -8
- data/vendor/libgit2/src/{email.c → libgit2/email.c} +55 -39
- data/vendor/libgit2/src/{email.h → libgit2/email.h} +1 -1
- data/vendor/libgit2/src/{errors.c → libgit2/errors.c} +18 -18
- data/vendor/libgit2/src/{errors.h → libgit2/errors.h} +1 -2
- data/vendor/libgit2/src/libgit2/experimental.h.in +13 -0
- data/vendor/libgit2/src/{fetch.c → libgit2/fetch.c} +72 -27
- data/vendor/libgit2/src/{fetch.h → libgit2/fetch.h} +1 -1
- data/vendor/libgit2/src/{fetchhead.c → libgit2/fetchhead.c} +23 -23
- data/vendor/libgit2/src/{filter.c → libgit2/filter.c} +127 -53
- data/vendor/libgit2/src/{filter.h → libgit2/filter.h} +26 -5
- data/vendor/libgit2/src/{ident.c → libgit2/ident.c} +20 -20
- data/vendor/libgit2/src/{ignore.c → libgit2/ignore.c} +35 -34
- data/vendor/libgit2/src/{ignore.h → libgit2/ignore.h} +2 -2
- data/vendor/libgit2/src/{index.c → libgit2/index.c} +91 -90
- data/vendor/libgit2/src/{index.h → libgit2/index.h} +6 -3
- data/vendor/libgit2/src/{indexer.c → libgit2/indexer.c} +173 -92
- data/vendor/libgit2/src/{iterator.c → libgit2/iterator.c} +71 -61
- data/vendor/libgit2/src/{iterator.h → libgit2/iterator.h} +5 -5
- data/vendor/libgit2/src/{libgit2.c → libgit2/libgit2.c} +46 -11
- data/vendor/libgit2/src/{mailmap.c → libgit2/mailmap.c} +38 -36
- data/vendor/libgit2/src/{merge.c → libgit2/merge.c} +30 -30
- data/vendor/libgit2/src/{merge.h → libgit2/merge.h} +1 -14
- data/vendor/libgit2/src/{merge_driver.c → libgit2/merge_driver.c} +2 -2
- data/vendor/libgit2/src/{merge_file.c → libgit2/merge_file.c} +13 -3
- data/vendor/libgit2/src/{message.c → libgit2/message.c} +21 -10
- data/vendor/libgit2/src/{midx.c → libgit2/midx.c} +112 -92
- data/vendor/libgit2/src/{midx.h → libgit2/midx.h} +5 -4
- data/vendor/libgit2/src/{mwindow.c → libgit2/mwindow.c} +15 -12
- data/vendor/libgit2/src/{mwindow.h → libgit2/mwindow.h} +5 -2
- data/vendor/libgit2/src/{netops.c → libgit2/netops.c} +1 -2
- data/vendor/libgit2/src/{netops.h → libgit2/netops.h} +1 -1
- data/vendor/libgit2/src/{notes.c → libgit2/notes.c} +25 -34
- data/vendor/libgit2/src/{object.c → libgit2/object.c} +135 -30
- data/vendor/libgit2/src/{object.h → libgit2/object.h} +12 -3
- data/vendor/libgit2/src/{odb.c → libgit2/odb.c} +228 -81
- data/vendor/libgit2/src/{odb.h → libgit2/odb.h} +44 -5
- data/vendor/libgit2/src/{odb_loose.c → libgit2/odb_loose.c} +192 -134
- data/vendor/libgit2/src/{odb_mempack.c → libgit2/odb_mempack.c} +18 -5
- data/vendor/libgit2/src/{odb_pack.c → libgit2/odb_pack.c} +137 -85
- data/vendor/libgit2/src/{oid.c → libgit2/oid.c} +136 -90
- data/vendor/libgit2/src/libgit2/oid.h +273 -0
- data/vendor/libgit2/src/{oidmap.c → libgit2/oidmap.c} +1 -1
- data/vendor/libgit2/src/{pack-objects.c → libgit2/pack-objects.c} +56 -30
- data/vendor/libgit2/src/{pack-objects.h → libgit2/pack-objects.h} +11 -6
- data/vendor/libgit2/src/{pack.c → libgit2/pack.c} +114 -84
- data/vendor/libgit2/src/{pack.h → libgit2/pack.h} +31 -16
- data/vendor/libgit2/src/{parse.c → libgit2/parse.c} +4 -3
- data/vendor/libgit2/src/{patch.c → libgit2/patch.c} +3 -3
- data/vendor/libgit2/src/{patch.h → libgit2/patch.h} +1 -0
- data/vendor/libgit2/src/{patch_generate.c → libgit2/patch_generate.c} +27 -11
- data/vendor/libgit2/src/{patch_generate.h → libgit2/patch_generate.h} +5 -5
- data/vendor/libgit2/src/{patch_parse.c → libgit2/patch_parse.c} +29 -29
- data/vendor/libgit2/src/libgit2/path.c +375 -0
- data/vendor/libgit2/src/libgit2/path.h +68 -0
- data/vendor/libgit2/src/{pathspec.c → libgit2/pathspec.c} +6 -6
- data/vendor/libgit2/src/{pathspec.h → libgit2/pathspec.h} +2 -2
- data/vendor/libgit2/src/{proxy.c → libgit2/proxy.c} +4 -1
- data/vendor/libgit2/src/{proxy.h → libgit2/proxy.h} +1 -1
- data/vendor/libgit2/src/{push.c → libgit2/push.c} +43 -38
- data/vendor/libgit2/src/{push.h → libgit2/push.h} +4 -16
- data/vendor/libgit2/src/{reader.c → libgit2/reader.c} +9 -9
- data/vendor/libgit2/src/{reader.h → libgit2/reader.h} +2 -2
- data/vendor/libgit2/src/{rebase.c → libgit2/rebase.c} +119 -107
- data/vendor/libgit2/src/{refdb_fs.c → libgit2/refdb_fs.c} +506 -197
- data/vendor/libgit2/src/{reflog.c → libgit2/reflog.c} +7 -5
- data/vendor/libgit2/src/{reflog.h → libgit2/reflog.h} +1 -2
- data/vendor/libgit2/src/{refs.c → libgit2/refs.c} +34 -32
- data/vendor/libgit2/src/{refs.h → libgit2/refs.h} +2 -2
- data/vendor/libgit2/src/{refspec.c → libgit2/refspec.c} +32 -37
- data/vendor/libgit2/src/{refspec.h → libgit2/refspec.h} +5 -2
- data/vendor/libgit2/src/{remote.c → libgit2/remote.c} +718 -420
- data/vendor/libgit2/src/libgit2/remote.h +100 -0
- data/vendor/libgit2/src/{repository.c → libgit2/repository.c} +629 -386
- data/vendor/libgit2/src/{repository.h → libgit2/repository.h} +20 -9
- data/vendor/libgit2/src/{reset.c → libgit2/reset.c} +8 -5
- data/vendor/libgit2/src/{revert.c → libgit2/revert.c} +14 -14
- data/vendor/libgit2/src/{revparse.c → libgit2/revparse.c} +71 -42
- data/vendor/libgit2/src/{revwalk.c → libgit2/revwalk.c} +12 -8
- data/vendor/libgit2/src/{signature.c → libgit2/signature.c} +12 -6
- data/vendor/libgit2/src/{signature.h → libgit2/signature.h} +1 -1
- data/vendor/libgit2/src/{stash.c → libgit2/stash.c} +235 -61
- data/vendor/libgit2/src/{status.c → libgit2/status.c} +4 -1
- data/vendor/libgit2/src/{strarray.c → libgit2/strarray.c} +1 -0
- data/vendor/libgit2/src/libgit2/strarray.h +25 -0
- data/vendor/libgit2/src/{streams → libgit2/streams}/mbedtls.c +8 -6
- data/vendor/libgit2/src/{streams → libgit2/streams}/openssl.c +1 -1
- data/vendor/libgit2/src/{streams → libgit2/streams}/openssl_dynamic.c +7 -3
- data/vendor/libgit2/src/{streams → libgit2/streams}/openssl_dynamic.h +3 -3
- data/vendor/libgit2/src/{streams → libgit2/streams}/socket.c +4 -1
- data/vendor/libgit2/src/{submodule.c → libgit2/submodule.c} +177 -161
- data/vendor/libgit2/src/{submodule.h → libgit2/submodule.h} +1 -1
- data/vendor/libgit2/src/libgit2/sysdir.c +650 -0
- data/vendor/libgit2/src/{sysdir.h → libgit2/sysdir.h} +53 -18
- data/vendor/libgit2/src/{tag.c → libgit2/tag.c} +73 -42
- data/vendor/libgit2/src/{tag.h → libgit2/tag.h} +2 -2
- data/vendor/libgit2/src/{threadstate.c → libgit2/threadstate.c} +3 -3
- data/vendor/libgit2/src/{threadstate.h → libgit2/threadstate.h} +2 -2
- data/vendor/libgit2/src/{trace.c → libgit2/trace.c} +1 -14
- data/vendor/libgit2/src/{trace.h → libgit2/trace.h} +5 -22
- data/vendor/libgit2/src/{trailer.c → libgit2/trailer.c} +1 -1
- data/vendor/libgit2/src/{transaction.c → libgit2/transaction.c} +1 -1
- data/vendor/libgit2/src/{transport.c → libgit2/transport.c} +10 -10
- data/vendor/libgit2/src/{transports → libgit2/transports}/auth.c +7 -9
- data/vendor/libgit2/src/{transports → libgit2/transports}/auth.h +2 -3
- data/vendor/libgit2/src/{transports → libgit2/transports}/auth_negotiate.c +12 -13
- data/vendor/libgit2/src/{transports → libgit2/transports}/auth_ntlm.c +10 -10
- data/vendor/libgit2/src/{transports → libgit2/transports}/auth_ntlm.h +0 -1
- data/vendor/libgit2/src/{transports → libgit2/transports}/git.c +9 -11
- data/vendor/libgit2/src/{transports → libgit2/transports}/http.c +41 -20
- data/vendor/libgit2/src/{transports → libgit2/transports}/http.h +2 -3
- data/vendor/libgit2/src/{transports → libgit2/transports}/httpclient.c +75 -66
- data/vendor/libgit2/src/{transports → libgit2/transports}/httpclient.h +10 -0
- data/vendor/libgit2/src/{transports → libgit2/transports}/local.c +138 -116
- data/vendor/libgit2/src/{transports → libgit2/transports}/smart.c +92 -133
- data/vendor/libgit2/src/{transports → libgit2/transports}/smart.h +35 -32
- data/vendor/libgit2/src/{transports → libgit2/transports}/smart_pkt.c +177 -65
- data/vendor/libgit2/src/{transports → libgit2/transports}/smart_protocol.c +97 -49
- data/vendor/libgit2/src/{transports → libgit2/transports}/ssh.c +365 -198
- data/vendor/libgit2/src/{transports → libgit2/transports}/winhttp.c +58 -59
- data/vendor/libgit2/src/{tree-cache.c → libgit2/tree-cache.c} +8 -8
- data/vendor/libgit2/src/{tree-cache.h → libgit2/tree-cache.h} +2 -2
- data/vendor/libgit2/src/{tree.c → libgit2/tree.c} +93 -83
- data/vendor/libgit2/src/{tree.h → libgit2/tree.h} +4 -4
- data/vendor/libgit2/src/{worktree.c → libgit2/worktree.c} +121 -94
- data/vendor/libgit2/src/{worktree.h → libgit2/worktree.h} +1 -1
- data/vendor/libgit2/src/libgit2/xdiff/git-xdiff.h +53 -0
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xdiff.h +15 -15
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xdiffi.c +134 -108
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xemit.c +23 -7
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xhistogram.c +87 -78
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xinclude.h +1 -12
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xmerge.c +104 -117
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xpatience.c +6 -17
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xprepare.c +15 -20
- data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xutils.c +18 -7
- data/vendor/libgit2/src/util/CMakeLists.txt +80 -0
- data/vendor/libgit2/src/{allocators → util/allocators}/failalloc.h +1 -1
- data/vendor/libgit2/src/{allocators → util/allocators}/stdalloc.h +1 -1
- data/vendor/libgit2/src/{allocators → util/allocators}/win32_leakcheck.h +1 -1
- data/vendor/libgit2/src/{array.h → util/array.h} +1 -1
- data/vendor/libgit2/src/{assert_safe.h → util/assert_safe.h} +16 -0
- data/vendor/libgit2/src/{cc-compat.h → util/cc-compat.h} +1 -1
- data/vendor/libgit2/src/{date.c → util/date.c} +14 -20
- data/vendor/libgit2/src/util/date.h +33 -0
- data/vendor/libgit2/src/{filebuf.c → util/filebuf.c} +29 -29
- data/vendor/libgit2/src/{filebuf.h → util/filebuf.h} +2 -2
- data/vendor/libgit2/src/{path.c → util/fs_path.c} +453 -647
- data/vendor/libgit2/src/{path.h → util/fs_path.h} +221 -188
- data/vendor/libgit2/src/{futils.c → util/futils.c} +135 -90
- data/vendor/libgit2/src/{futils.h → util/futils.h} +28 -15
- data/vendor/libgit2/src/{features.h.in → util/git2_features.h.in} +15 -1
- data/vendor/libgit2/src/{common.h → util/git2_util.h} +20 -59
- data/vendor/libgit2/src/util/hash/builtin.c +53 -0
- data/vendor/libgit2/src/{hash/sha1/openssl.h → util/hash/builtin.h} +6 -6
- data/vendor/libgit2/src/{hash/sha1 → util/hash}/collisiondetect.c +3 -3
- data/vendor/libgit2/src/{hash/sha1 → util/hash}/collisiondetect.h +3 -3
- data/vendor/libgit2/src/util/hash/common_crypto.c +112 -0
- data/vendor/libgit2/src/{hash/sha1 → util/hash}/common_crypto.h +11 -3
- data/vendor/libgit2/src/util/hash/mbedtls.c +92 -0
- data/vendor/libgit2/src/{hash/sha1 → util/hash}/mbedtls.h +14 -4
- data/vendor/libgit2/src/util/hash/openssl.c +195 -0
- data/vendor/libgit2/src/util/hash/openssl.h +45 -0
- data/vendor/libgit2/src/util/hash/rfc6234/sha.h +243 -0
- data/vendor/libgit2/src/util/hash/rfc6234/sha224-256.c +601 -0
- data/vendor/libgit2/src/util/hash/sha.h +70 -0
- data/vendor/libgit2/src/{hash/sha1 → util/hash}/sha1dc/sha1.c +1 -1
- data/vendor/libgit2/src/util/hash/win32.c +549 -0
- data/vendor/libgit2/src/util/hash/win32.h +60 -0
- data/vendor/libgit2/src/util/hash.c +158 -0
- data/vendor/libgit2/src/util/hash.h +61 -0
- data/vendor/libgit2/src/{khash.h → util/khash.h} +1 -1
- data/vendor/libgit2/src/{map.h → util/map.h} +1 -1
- data/vendor/libgit2/src/util/net.c +1003 -0
- data/vendor/libgit2/src/{net.h → util/net.h} +18 -4
- data/vendor/libgit2/src/{pool.h → util/pool.h} +1 -1
- data/vendor/libgit2/src/{posix.c → util/posix.c} +3 -3
- data/vendor/libgit2/src/{posix.h → util/posix.h} +4 -1
- data/vendor/libgit2/src/{pqueue.h → util/pqueue.h} +2 -2
- data/vendor/libgit2/src/util/rand.c +234 -0
- data/vendor/libgit2/src/util/rand.h +37 -0
- data/vendor/libgit2/src/{regexp.c → util/regexp.c} +4 -4
- data/vendor/libgit2/src/{regexp.h → util/regexp.h} +1 -1
- data/vendor/libgit2/src/{runtime.c → util/runtime.c} +1 -1
- data/vendor/libgit2/src/{runtime.h → util/runtime.h} +1 -1
- data/vendor/libgit2/src/{sortedcache.c → util/sortedcache.c} +1 -1
- data/vendor/libgit2/src/{sortedcache.h → util/sortedcache.h} +2 -2
- data/vendor/libgit2/src/{buffer.c → util/str.c} +157 -151
- data/vendor/libgit2/src/util/str.h +357 -0
- data/vendor/libgit2/src/{strmap.h → util/strmap.h} +1 -1
- data/vendor/libgit2/src/{thread.c → util/thread.c} +1 -1
- data/vendor/libgit2/src/{thread.h → util/thread.h} +23 -22
- data/vendor/libgit2/src/{tsort.c → util/tsort.c} +1 -1
- data/vendor/libgit2/src/{unix → util/unix}/map.c +1 -3
- data/vendor/libgit2/src/{unix → util/unix}/posix.h +1 -4
- data/vendor/libgit2/src/{unix → util/unix}/realpath.c +1 -3
- data/vendor/libgit2/src/{utf8.c → util/utf8.c} +1 -1
- data/vendor/libgit2/src/{utf8.h → util/utf8.h} +1 -1
- data/vendor/libgit2/src/{util.c → util/util.c} +15 -15
- data/vendor/libgit2/src/{util.h → util/util.h} +4 -29
- data/vendor/libgit2/src/{varint.h → util/varint.h} +1 -1
- data/vendor/libgit2/src/{vector.h → util/vector.h} +2 -2
- data/vendor/libgit2/src/{wildmatch.h → util/wildmatch.h} +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/dir.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/error.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/map.c +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/path_w32.c +140 -9
- data/vendor/libgit2/src/{win32 → util/win32}/path_w32.h +3 -1
- data/vendor/libgit2/src/{win32 → util/win32}/posix.h +1 -2
- data/vendor/libgit2/src/{win32 → util/win32}/posix_w32.c +12 -28
- data/vendor/libgit2/src/util/win32/precompiled.c +1 -0
- data/vendor/libgit2/src/{win32 → util/win32}/precompiled.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/thread.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/utf-conv.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/w32_buffer.c +2 -3
- data/vendor/libgit2/src/{win32 → util/win32}/w32_buffer.h +3 -4
- data/vendor/libgit2/src/{win32 → util/win32}/w32_leakcheck.c +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/w32_leakcheck.h +1 -1
- data/vendor/libgit2/src/{win32 → util/win32}/w32_util.h +1 -1
- data/vendor/libgit2/src/{zstream.c → util/zstream.c} +5 -5
- data/vendor/libgit2/src/{zstream.h → util/zstream.h} +5 -5
- metadata +402 -356
- data/vendor/libgit2/src/buffer.h +0 -374
- data/vendor/libgit2/src/commit.h +0 -46
- data/vendor/libgit2/src/hash/sha1/common_crypto.c +0 -57
- data/vendor/libgit2/src/hash/sha1/generic.c +0 -300
- data/vendor/libgit2/src/hash/sha1/generic.h +0 -19
- data/vendor/libgit2/src/hash/sha1/mbedtls.c +0 -46
- data/vendor/libgit2/src/hash/sha1/openssl.c +0 -59
- data/vendor/libgit2/src/hash/sha1/win32.c +0 -333
- data/vendor/libgit2/src/hash/sha1/win32.h +0 -128
- data/vendor/libgit2/src/hash/sha1.h +0 -38
- data/vendor/libgit2/src/hash.c +0 -110
- data/vendor/libgit2/src/hash.h +0 -46
- data/vendor/libgit2/src/message.h +0 -17
- data/vendor/libgit2/src/net.c +0 -540
- data/vendor/libgit2/src/oid.h +0 -51
- data/vendor/libgit2/src/remote.h +0 -55
- data/vendor/libgit2/src/sysdir.c +0 -347
- data/vendor/libgit2/src/win32/findfile.c +0 -230
- data/vendor/libgit2/src/win32/findfile.h +0 -19
- /data/vendor/libgit2/src/{win32 → cli/win32}/precompiled.c +0 -0
- /data/vendor/libgit2/src/{attr.h → libgit2/attr.h} +0 -0
- /data/vendor/libgit2/src/{attrcache.h → libgit2/attrcache.h} +0 -0
- /data/vendor/libgit2/src/{blame.h → libgit2/blame.h} +0 -0
- /data/vendor/libgit2/src/{blame_git.h → libgit2/blame_git.h} +0 -0
- /data/vendor/libgit2/src/{cache.c → libgit2/cache.c} +0 -0
- /data/vendor/libgit2/src/{cache.h → libgit2/cache.h} +0 -0
- /data/vendor/libgit2/src/{checkout.h → libgit2/checkout.h} +0 -0
- /data/vendor/libgit2/src/{clone.h → libgit2/clone.h} +0 -0
- /data/vendor/libgit2/src/{commit_list.h → libgit2/commit_list.h} +0 -0
- /data/vendor/libgit2/src/{config_backend.h → libgit2/config_backend.h} +0 -0
- /data/vendor/libgit2/src/{config_cache.c → libgit2/config_cache.c} +0 -0
- /data/vendor/libgit2/src/{config_entries.c → libgit2/config_entries.c} +0 -0
- /data/vendor/libgit2/src/{config_entries.h → libgit2/config_entries.h} +0 -0
- /data/vendor/libgit2/src/{config_parse.h → libgit2/config_parse.h} +0 -0
- /data/vendor/libgit2/src/{config_snapshot.c → libgit2/config_snapshot.c} +0 -0
- /data/vendor/libgit2/src/{delta.c → libgit2/delta.c} +0 -0
- /data/vendor/libgit2/src/{delta.h → libgit2/delta.h} +0 -0
- /data/vendor/libgit2/src/{diff_file.h → libgit2/diff_file.h} +0 -0
- /data/vendor/libgit2/src/{diff_parse.c → libgit2/diff_parse.c} +0 -0
- /data/vendor/libgit2/src/{diff_parse.h → libgit2/diff_parse.h} +0 -0
- /data/vendor/libgit2/src/{diff_tform.h → libgit2/diff_tform.h} +0 -0
- /data/vendor/libgit2/src/{diff_xdiff.h → libgit2/diff_xdiff.h} +0 -0
- /data/vendor/libgit2/src/{fetchhead.h → libgit2/fetchhead.h} +0 -0
- /data/vendor/libgit2/src/{win32 → libgit2}/git2.rc +0 -0
- /data/vendor/libgit2/src/{graph.c → libgit2/graph.c} +0 -0
- /data/vendor/libgit2/src/{hashsig.c → libgit2/hashsig.c} +0 -0
- /data/vendor/libgit2/src/{idxmap.c → libgit2/idxmap.c} +0 -0
- /data/vendor/libgit2/src/{idxmap.h → libgit2/idxmap.h} +0 -0
- /data/vendor/libgit2/src/{indexer.h → libgit2/indexer.h} +0 -0
- /data/vendor/libgit2/src/{libgit2.h → libgit2/libgit2.h} +0 -0
- /data/vendor/libgit2/src/{mailmap.h → libgit2/mailmap.h} +0 -0
- /data/vendor/libgit2/src/{merge_driver.h → libgit2/merge_driver.h} +0 -0
- /data/vendor/libgit2/src/{notes.h → libgit2/notes.h} +0 -0
- /data/vendor/libgit2/src/{object_api.c → libgit2/object_api.c} +0 -0
- /data/vendor/libgit2/src/{offmap.c → libgit2/offmap.c} +0 -0
- /data/vendor/libgit2/src/{offmap.h → libgit2/offmap.h} +0 -0
- /data/vendor/libgit2/src/{oidarray.c → libgit2/oidarray.c} +0 -0
- /data/vendor/libgit2/src/{oidarray.h → libgit2/oidarray.h} +0 -0
- /data/vendor/libgit2/src/{oidmap.h → libgit2/oidmap.h} +0 -0
- /data/vendor/libgit2/src/{parse.h → libgit2/parse.h} +0 -0
- /data/vendor/libgit2/src/{patch_parse.h → libgit2/patch_parse.h} +0 -0
- /data/vendor/libgit2/src/{refdb.c → libgit2/refdb.c} +0 -0
- /data/vendor/libgit2/src/{refdb.h → libgit2/refdb.h} +0 -0
- /data/vendor/libgit2/src/{repo_template.h → libgit2/repo_template.h} +0 -0
- /data/vendor/libgit2/src/{revwalk.h → libgit2/revwalk.h} +0 -0
- /data/vendor/libgit2/src/{settings.h → libgit2/settings.h} +0 -0
- /data/vendor/libgit2/src/{status.h → libgit2/status.h} +0 -0
- /data/vendor/libgit2/src/{stream.h → libgit2/stream.h} +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/mbedtls.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/openssl.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/openssl_legacy.c +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/openssl_legacy.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/registry.c +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/registry.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/socket.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/stransport.c +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/stransport.h +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/tls.c +0 -0
- /data/vendor/libgit2/src/{streams → libgit2/streams}/tls.h +0 -0
- /data/vendor/libgit2/src/{transaction.h → libgit2/transaction.h} +0 -0
- /data/vendor/libgit2/src/{transports → libgit2/transports}/auth_negotiate.h +0 -0
- /data/vendor/libgit2/src/{transports → libgit2/transports}/credential.c +0 -0
- /data/vendor/libgit2/src/{transports → libgit2/transports}/credential_helpers.c +0 -0
- /data/vendor/libgit2/src/{transports → libgit2/transports}/ssh.h +0 -0
- /data/vendor/libgit2/src/{userdiff.h → libgit2/userdiff.h} +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xdiffi.h +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xemit.h +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xmacros.h +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xprepare.h +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xtypes.h +0 -0
- /data/vendor/libgit2/src/{xdiff → libgit2/xdiff}/xutils.h +0 -0
- /data/vendor/libgit2/src/{alloc.c → util/alloc.c} +0 -0
- /data/vendor/libgit2/src/{alloc.h → util/alloc.h} +0 -0
- /data/vendor/libgit2/src/{allocators → util/allocators}/failalloc.c +0 -0
- /data/vendor/libgit2/src/{allocators → util/allocators}/stdalloc.c +0 -0
- /data/vendor/libgit2/src/{allocators → util/allocators}/win32_leakcheck.c +0 -0
- /data/vendor/libgit2/src/{bitvec.h → util/bitvec.h} +0 -0
- /data/vendor/libgit2/src/{hash/sha1 → util/hash}/sha1dc/sha1.h +0 -0
- /data/vendor/libgit2/src/{hash/sha1 → util/hash}/sha1dc/ubc_check.c +0 -0
- /data/vendor/libgit2/src/{hash/sha1 → util/hash}/sha1dc/ubc_check.h +0 -0
- /data/vendor/libgit2/src/{integer.h → util/integer.h} +0 -0
- /data/vendor/libgit2/src/{pool.c → util/pool.c} +0 -0
- /data/vendor/libgit2/src/{pqueue.c → util/pqueue.c} +0 -0
- /data/vendor/libgit2/src/{strmap.c → util/strmap.c} +0 -0
- /data/vendor/libgit2/src/{strnlen.h → util/strnlen.h} +0 -0
- /data/vendor/libgit2/src/{unix → util/unix}/pthread.h +0 -0
- /data/vendor/libgit2/src/{varint.c → util/varint.c} +0 -0
- /data/vendor/libgit2/src/{vector.c → util/vector.c} +0 -0
- /data/vendor/libgit2/src/{wildmatch.c → util/wildmatch.c} +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/dir.c +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/error.c +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/mingw-compat.h +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/msvc-compat.h +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/reparse.h +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/thread.c +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/utf-conv.c +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/version.h +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/w32_common.h +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/w32_util.c +0 -0
- /data/vendor/libgit2/src/{win32 → util/win32}/win32-compat.h +0 -0
|
@@ -5,10 +5,11 @@
|
|
|
5
5
|
* a Linking Exception. For full terms see the included COPYING file.
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
-
#include "
|
|
8
|
+
#include "fs_path.h"
|
|
9
9
|
|
|
10
|
+
#include "git2_util.h"
|
|
11
|
+
#include "futils.h"
|
|
10
12
|
#include "posix.h"
|
|
11
|
-
#include "repository.h"
|
|
12
13
|
#ifdef GIT_WIN32
|
|
13
14
|
#include "win32/posix.h"
|
|
14
15
|
#include "win32/w32_buffer.h"
|
|
@@ -21,6 +22,13 @@
|
|
|
21
22
|
#include <stdio.h>
|
|
22
23
|
#include <ctype.h>
|
|
23
24
|
|
|
25
|
+
#define ensure_error_set(code) do { \
|
|
26
|
+
const git_error *e = git_error_last(); \
|
|
27
|
+
if (!e || !e->message) \
|
|
28
|
+
git_error_set(e ? e->klass : GIT_ERROR_CALLBACK, \
|
|
29
|
+
"filesystem callback returned %d", code); \
|
|
30
|
+
} while(0)
|
|
31
|
+
|
|
24
32
|
static int dos_drive_prefix_length(const char *path)
|
|
25
33
|
{
|
|
26
34
|
int i;
|
|
@@ -93,7 +101,7 @@ static bool looks_like_network_computer_name(const char *path, int pos)
|
|
|
93
101
|
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
|
94
102
|
* SUCH DAMAGE.
|
|
95
103
|
*/
|
|
96
|
-
int
|
|
104
|
+
int git_fs_path_basename_r(git_str *buffer, const char *path)
|
|
97
105
|
{
|
|
98
106
|
const char *endp, *startp;
|
|
99
107
|
int len, result;
|
|
@@ -101,7 +109,7 @@ int git_path_basename_r(git_buf *buffer, const char *path)
|
|
|
101
109
|
/* Empty or NULL string gets treated as "." */
|
|
102
110
|
if (path == NULL || *path == '\0') {
|
|
103
111
|
startp = ".";
|
|
104
|
-
len
|
|
112
|
+
len = 1;
|
|
105
113
|
goto Exit;
|
|
106
114
|
}
|
|
107
115
|
|
|
@@ -113,7 +121,7 @@ int git_path_basename_r(git_buf *buffer, const char *path)
|
|
|
113
121
|
/* All slashes becomes "/" */
|
|
114
122
|
if (endp == path && *endp == '/') {
|
|
115
123
|
startp = "/";
|
|
116
|
-
len
|
|
124
|
+
len = 1;
|
|
117
125
|
goto Exit;
|
|
118
126
|
}
|
|
119
127
|
|
|
@@ -128,7 +136,7 @@ int git_path_basename_r(git_buf *buffer, const char *path)
|
|
|
128
136
|
Exit:
|
|
129
137
|
result = len;
|
|
130
138
|
|
|
131
|
-
if (buffer != NULL &&
|
|
139
|
+
if (buffer != NULL && git_str_set(buffer, startp, len) < 0)
|
|
132
140
|
return -1;
|
|
133
141
|
|
|
134
142
|
return result;
|
|
@@ -136,7 +144,7 @@ Exit:
|
|
|
136
144
|
|
|
137
145
|
/*
|
|
138
146
|
* Determine if the path is a Windows prefix and, if so, returns
|
|
139
|
-
* its actual
|
|
147
|
+
* its actual length. If it is not a prefix, returns -1.
|
|
140
148
|
*/
|
|
141
149
|
static int win32_prefix_length(const char *path, int len)
|
|
142
150
|
{
|
|
@@ -166,7 +174,7 @@ static int win32_prefix_length(const char *path, int len)
|
|
|
166
174
|
* Based on the Android implementation, BSD licensed.
|
|
167
175
|
* Check http://android.git.kernel.org/
|
|
168
176
|
*/
|
|
169
|
-
int
|
|
177
|
+
int git_fs_path_dirname_r(git_str *buffer, const char *path)
|
|
170
178
|
{
|
|
171
179
|
const char *endp;
|
|
172
180
|
int is_prefix = 0, len;
|
|
@@ -185,8 +193,7 @@ int git_path_dirname_r(git_buf *buffer, const char *path)
|
|
|
185
193
|
|
|
186
194
|
if (endp - path + 1 > INT_MAX) {
|
|
187
195
|
git_error_set(GIT_ERROR_INVALID, "path too long");
|
|
188
|
-
|
|
189
|
-
goto Exit;
|
|
196
|
+
return -1;
|
|
190
197
|
}
|
|
191
198
|
|
|
192
199
|
if ((len = win32_prefix_length(path, (int)(endp - path + 1))) > 0) {
|
|
@@ -211,8 +218,7 @@ int git_path_dirname_r(git_buf *buffer, const char *path)
|
|
|
211
218
|
|
|
212
219
|
if (endp - path + 1 > INT_MAX) {
|
|
213
220
|
git_error_set(GIT_ERROR_INVALID, "path too long");
|
|
214
|
-
|
|
215
|
-
goto Exit;
|
|
221
|
+
return -1;
|
|
216
222
|
}
|
|
217
223
|
|
|
218
224
|
if ((len = win32_prefix_length(path, (int)(endp - path + 1))) > 0) {
|
|
@@ -225,9 +231,9 @@ int git_path_dirname_r(git_buf *buffer, const char *path)
|
|
|
225
231
|
|
|
226
232
|
Exit:
|
|
227
233
|
if (buffer) {
|
|
228
|
-
if (
|
|
234
|
+
if (git_str_set(buffer, path, len) < 0)
|
|
229
235
|
return -1;
|
|
230
|
-
if (is_prefix &&
|
|
236
|
+
if (is_prefix && git_str_putc(buffer, '/') < 0)
|
|
231
237
|
return -1;
|
|
232
238
|
}
|
|
233
239
|
|
|
@@ -235,38 +241,38 @@ Exit:
|
|
|
235
241
|
}
|
|
236
242
|
|
|
237
243
|
|
|
238
|
-
char *
|
|
244
|
+
char *git_fs_path_dirname(const char *path)
|
|
239
245
|
{
|
|
240
|
-
|
|
246
|
+
git_str buf = GIT_STR_INIT;
|
|
241
247
|
char *dirname;
|
|
242
248
|
|
|
243
|
-
|
|
244
|
-
dirname =
|
|
245
|
-
|
|
249
|
+
git_fs_path_dirname_r(&buf, path);
|
|
250
|
+
dirname = git_str_detach(&buf);
|
|
251
|
+
git_str_dispose(&buf); /* avoid memleak if error occurs */
|
|
246
252
|
|
|
247
253
|
return dirname;
|
|
248
254
|
}
|
|
249
255
|
|
|
250
|
-
char *
|
|
256
|
+
char *git_fs_path_basename(const char *path)
|
|
251
257
|
{
|
|
252
|
-
|
|
258
|
+
git_str buf = GIT_STR_INIT;
|
|
253
259
|
char *basename;
|
|
254
260
|
|
|
255
|
-
|
|
256
|
-
basename =
|
|
257
|
-
|
|
261
|
+
git_fs_path_basename_r(&buf, path);
|
|
262
|
+
basename = git_str_detach(&buf);
|
|
263
|
+
git_str_dispose(&buf); /* avoid memleak if error occurs */
|
|
258
264
|
|
|
259
265
|
return basename;
|
|
260
266
|
}
|
|
261
267
|
|
|
262
|
-
size_t
|
|
268
|
+
size_t git_fs_path_basename_offset(git_str *buffer)
|
|
263
269
|
{
|
|
264
270
|
ssize_t slash;
|
|
265
271
|
|
|
266
272
|
if (!buffer || buffer->size <= 0)
|
|
267
273
|
return 0;
|
|
268
274
|
|
|
269
|
-
slash =
|
|
275
|
+
slash = git_str_rfind_next(buffer, '/');
|
|
270
276
|
|
|
271
277
|
if (slash >= 0 && buffer->ptr[slash] == '/')
|
|
272
278
|
return (size_t)(slash + 1);
|
|
@@ -274,7 +280,7 @@ size_t git_path_basename_offset(git_buf *buffer)
|
|
|
274
280
|
return 0;
|
|
275
281
|
}
|
|
276
282
|
|
|
277
|
-
int
|
|
283
|
+
int git_fs_path_root(const char *path)
|
|
278
284
|
{
|
|
279
285
|
int offset = 0, prefix_len;
|
|
280
286
|
|
|
@@ -304,9 +310,9 @@ int git_path_root(const char *path)
|
|
|
304
310
|
return -1; /* Not a real error - signals that path is not rooted */
|
|
305
311
|
}
|
|
306
312
|
|
|
307
|
-
static void path_trim_slashes(
|
|
313
|
+
static void path_trim_slashes(git_str *path)
|
|
308
314
|
{
|
|
309
|
-
int ceiling =
|
|
315
|
+
int ceiling = git_fs_path_root(path->ptr) + 1;
|
|
310
316
|
|
|
311
317
|
if (ceiling < 0)
|
|
312
318
|
return;
|
|
@@ -320,29 +326,29 @@ static void path_trim_slashes(git_buf *path)
|
|
|
320
326
|
}
|
|
321
327
|
}
|
|
322
328
|
|
|
323
|
-
int
|
|
324
|
-
|
|
329
|
+
int git_fs_path_join_unrooted(
|
|
330
|
+
git_str *path_out, const char *path, const char *base, ssize_t *root_at)
|
|
325
331
|
{
|
|
326
332
|
ssize_t root;
|
|
327
333
|
|
|
328
334
|
GIT_ASSERT_ARG(path_out);
|
|
329
335
|
GIT_ASSERT_ARG(path);
|
|
330
336
|
|
|
331
|
-
root = (ssize_t)
|
|
337
|
+
root = (ssize_t)git_fs_path_root(path);
|
|
332
338
|
|
|
333
339
|
if (base != NULL && root < 0) {
|
|
334
|
-
if (
|
|
340
|
+
if (git_str_joinpath(path_out, base, path) < 0)
|
|
335
341
|
return -1;
|
|
336
342
|
|
|
337
343
|
root = (ssize_t)strlen(base);
|
|
338
344
|
} else {
|
|
339
|
-
if (
|
|
345
|
+
if (git_str_sets(path_out, path) < 0)
|
|
340
346
|
return -1;
|
|
341
347
|
|
|
342
348
|
if (root < 0)
|
|
343
349
|
root = 0;
|
|
344
350
|
else if (base)
|
|
345
|
-
|
|
351
|
+
git_fs_path_equal_or_prefixed(base, path, &root);
|
|
346
352
|
}
|
|
347
353
|
|
|
348
354
|
if (root_at)
|
|
@@ -351,7 +357,7 @@ int git_path_join_unrooted(
|
|
|
351
357
|
return 0;
|
|
352
358
|
}
|
|
353
359
|
|
|
354
|
-
void
|
|
360
|
+
void git_fs_path_squash_slashes(git_str *path)
|
|
355
361
|
{
|
|
356
362
|
char *p, *q;
|
|
357
363
|
|
|
@@ -370,7 +376,7 @@ void git_path_squash_slashes(git_buf *path)
|
|
|
370
376
|
*p = '\0';
|
|
371
377
|
}
|
|
372
378
|
|
|
373
|
-
int
|
|
379
|
+
int git_fs_path_prettify(git_str *path_out, const char *path, const char *base)
|
|
374
380
|
{
|
|
375
381
|
char buf[GIT_PATH_MAX];
|
|
376
382
|
|
|
@@ -378,8 +384,8 @@ int git_path_prettify(git_buf *path_out, const char *path, const char *base)
|
|
|
378
384
|
GIT_ASSERT_ARG(path);
|
|
379
385
|
|
|
380
386
|
/* construct path if needed */
|
|
381
|
-
if (base != NULL &&
|
|
382
|
-
if (
|
|
387
|
+
if (base != NULL && git_fs_path_root(path) < 0) {
|
|
388
|
+
if (git_str_joinpath(path_out, base, path) < 0)
|
|
383
389
|
return -1;
|
|
384
390
|
path = path_out->ptr;
|
|
385
391
|
}
|
|
@@ -389,31 +395,31 @@ int git_path_prettify(git_buf *path_out, const char *path, const char *base)
|
|
|
389
395
|
int error = (errno == ENOENT || errno == ENOTDIR) ? GIT_ENOTFOUND : -1;
|
|
390
396
|
git_error_set(GIT_ERROR_OS, "failed to resolve path '%s'", path);
|
|
391
397
|
|
|
392
|
-
|
|
398
|
+
git_str_clear(path_out);
|
|
393
399
|
|
|
394
400
|
return error;
|
|
395
401
|
}
|
|
396
402
|
|
|
397
|
-
return
|
|
403
|
+
return git_str_sets(path_out, buf);
|
|
398
404
|
}
|
|
399
405
|
|
|
400
|
-
int
|
|
406
|
+
int git_fs_path_prettify_dir(git_str *path_out, const char *path, const char *base)
|
|
401
407
|
{
|
|
402
|
-
int error =
|
|
403
|
-
return (error < 0) ? error :
|
|
408
|
+
int error = git_fs_path_prettify(path_out, path, base);
|
|
409
|
+
return (error < 0) ? error : git_fs_path_to_dir(path_out);
|
|
404
410
|
}
|
|
405
411
|
|
|
406
|
-
int
|
|
412
|
+
int git_fs_path_to_dir(git_str *path)
|
|
407
413
|
{
|
|
408
414
|
if (path->asize > 0 &&
|
|
409
|
-
|
|
410
|
-
path->ptr[
|
|
411
|
-
|
|
415
|
+
git_str_len(path) > 0 &&
|
|
416
|
+
path->ptr[git_str_len(path) - 1] != '/')
|
|
417
|
+
git_str_putc(path, '/');
|
|
412
418
|
|
|
413
|
-
return
|
|
419
|
+
return git_str_oom(path) ? -1 : 0;
|
|
414
420
|
}
|
|
415
421
|
|
|
416
|
-
void
|
|
422
|
+
void git_fs_path_string_to_dir(char *path, size_t size)
|
|
417
423
|
{
|
|
418
424
|
size_t end = strlen(path);
|
|
419
425
|
|
|
@@ -423,7 +429,7 @@ void git_path_string_to_dir(char *path, size_t size)
|
|
|
423
429
|
}
|
|
424
430
|
}
|
|
425
431
|
|
|
426
|
-
int git__percent_decode(
|
|
432
|
+
int git__percent_decode(git_str *decoded_out, const char *input)
|
|
427
433
|
{
|
|
428
434
|
int len, hi, lo, i;
|
|
429
435
|
|
|
@@ -431,7 +437,7 @@ int git__percent_decode(git_buf *decoded_out, const char *input)
|
|
|
431
437
|
GIT_ASSERT_ARG(input);
|
|
432
438
|
|
|
433
439
|
len = (int)strlen(input);
|
|
434
|
-
|
|
440
|
+
git_str_clear(decoded_out);
|
|
435
441
|
|
|
436
442
|
for(i = 0; i < len; i++)
|
|
437
443
|
{
|
|
@@ -453,7 +459,7 @@ int git__percent_decode(git_buf *decoded_out, const char *input)
|
|
|
453
459
|
i += 2;
|
|
454
460
|
|
|
455
461
|
append:
|
|
456
|
-
if (
|
|
462
|
+
if (git_str_putc(decoded_out, c) < 0)
|
|
457
463
|
return -1;
|
|
458
464
|
}
|
|
459
465
|
|
|
@@ -480,12 +486,12 @@ static int local_file_url_prefixlen(const char *file_url)
|
|
|
480
486
|
return len;
|
|
481
487
|
}
|
|
482
488
|
|
|
483
|
-
bool
|
|
489
|
+
bool git_fs_path_is_local_file_url(const char *file_url)
|
|
484
490
|
{
|
|
485
491
|
return (local_file_url_prefixlen(file_url) > 0);
|
|
486
492
|
}
|
|
487
493
|
|
|
488
|
-
int
|
|
494
|
+
int git_fs_path_fromurl(git_str *local_path_out, const char *file_url)
|
|
489
495
|
{
|
|
490
496
|
int offset;
|
|
491
497
|
|
|
@@ -500,18 +506,18 @@ int git_path_fromurl(git_buf *local_path_out, const char *file_url)
|
|
|
500
506
|
offset--; /* A *nix absolute path starts with a forward slash */
|
|
501
507
|
#endif
|
|
502
508
|
|
|
503
|
-
|
|
509
|
+
git_str_clear(local_path_out);
|
|
504
510
|
return git__percent_decode(local_path_out, file_url + offset);
|
|
505
511
|
}
|
|
506
512
|
|
|
507
|
-
int
|
|
508
|
-
|
|
513
|
+
int git_fs_path_walk_up(
|
|
514
|
+
git_str *path,
|
|
509
515
|
const char *ceiling,
|
|
510
516
|
int (*cb)(void *data, const char *),
|
|
511
517
|
void *data)
|
|
512
518
|
{
|
|
513
519
|
int error = 0;
|
|
514
|
-
|
|
520
|
+
git_str iter;
|
|
515
521
|
ssize_t stop = 0, scan;
|
|
516
522
|
char oldc = '\0';
|
|
517
523
|
|
|
@@ -522,20 +528,20 @@ int git_path_walk_up(
|
|
|
522
528
|
if (git__prefixcmp(path->ptr, ceiling) == 0)
|
|
523
529
|
stop = (ssize_t)strlen(ceiling);
|
|
524
530
|
else
|
|
525
|
-
stop =
|
|
531
|
+
stop = git_str_len(path);
|
|
526
532
|
}
|
|
527
|
-
scan =
|
|
533
|
+
scan = git_str_len(path);
|
|
528
534
|
|
|
529
535
|
/* empty path: yield only once */
|
|
530
536
|
if (!scan) {
|
|
531
537
|
error = cb(data, "");
|
|
532
538
|
if (error)
|
|
533
|
-
|
|
539
|
+
ensure_error_set(error);
|
|
534
540
|
return error;
|
|
535
541
|
}
|
|
536
542
|
|
|
537
543
|
iter.ptr = path->ptr;
|
|
538
|
-
iter.size =
|
|
544
|
+
iter.size = git_str_len(path);
|
|
539
545
|
iter.asize = path->asize;
|
|
540
546
|
|
|
541
547
|
while (scan >= stop) {
|
|
@@ -543,11 +549,11 @@ int git_path_walk_up(
|
|
|
543
549
|
iter.ptr[scan] = oldc;
|
|
544
550
|
|
|
545
551
|
if (error) {
|
|
546
|
-
|
|
552
|
+
ensure_error_set(error);
|
|
547
553
|
break;
|
|
548
554
|
}
|
|
549
555
|
|
|
550
|
-
scan =
|
|
556
|
+
scan = git_str_rfind_next(&iter, '/');
|
|
551
557
|
if (scan >= 0) {
|
|
552
558
|
scan++;
|
|
553
559
|
oldc = iter.ptr[scan];
|
|
@@ -563,19 +569,19 @@ int git_path_walk_up(
|
|
|
563
569
|
if (!error && stop == 0 && iter.ptr[0] != '/') {
|
|
564
570
|
error = cb(data, "");
|
|
565
571
|
if (error)
|
|
566
|
-
|
|
572
|
+
ensure_error_set(error);
|
|
567
573
|
}
|
|
568
574
|
|
|
569
575
|
return error;
|
|
570
576
|
}
|
|
571
577
|
|
|
572
|
-
bool
|
|
578
|
+
bool git_fs_path_exists(const char *path)
|
|
573
579
|
{
|
|
574
580
|
GIT_ASSERT_ARG_WITH_RETVAL(path, false);
|
|
575
581
|
return p_access(path, F_OK) == 0;
|
|
576
582
|
}
|
|
577
583
|
|
|
578
|
-
bool
|
|
584
|
+
bool git_fs_path_isdir(const char *path)
|
|
579
585
|
{
|
|
580
586
|
struct stat st;
|
|
581
587
|
if (p_stat(path, &st) < 0)
|
|
@@ -584,7 +590,7 @@ bool git_path_isdir(const char *path)
|
|
|
584
590
|
return S_ISDIR(st.st_mode) != 0;
|
|
585
591
|
}
|
|
586
592
|
|
|
587
|
-
bool
|
|
593
|
+
bool git_fs_path_isfile(const char *path)
|
|
588
594
|
{
|
|
589
595
|
struct stat st;
|
|
590
596
|
|
|
@@ -595,7 +601,7 @@ bool git_path_isfile(const char *path)
|
|
|
595
601
|
return S_ISREG(st.st_mode) != 0;
|
|
596
602
|
}
|
|
597
603
|
|
|
598
|
-
bool
|
|
604
|
+
bool git_fs_path_islink(const char *path)
|
|
599
605
|
{
|
|
600
606
|
struct stat st;
|
|
601
607
|
|
|
@@ -608,7 +614,7 @@ bool git_path_islink(const char *path)
|
|
|
608
614
|
|
|
609
615
|
#ifdef GIT_WIN32
|
|
610
616
|
|
|
611
|
-
bool
|
|
617
|
+
bool git_fs_path_is_empty_dir(const char *path)
|
|
612
618
|
{
|
|
613
619
|
git_win32_path filter_w;
|
|
614
620
|
bool empty = false;
|
|
@@ -627,7 +633,7 @@ bool git_path_is_empty_dir(const char *path)
|
|
|
627
633
|
* (a mount point).
|
|
628
634
|
*/
|
|
629
635
|
if (hFind == INVALID_HANDLE_VALUE)
|
|
630
|
-
return
|
|
636
|
+
return git_fs_path_isdir(path);
|
|
631
637
|
|
|
632
638
|
/* If the find handle was created successfully, then it's a directory */
|
|
633
639
|
empty = true;
|
|
@@ -637,7 +643,7 @@ bool git_path_is_empty_dir(const char *path)
|
|
|
637
643
|
* empty. In the special case of drive roots (i.e. C:\) where . and
|
|
638
644
|
* .. do not occur, we can still consider the path to be an empty
|
|
639
645
|
* directory if there's nothing there. */
|
|
640
|
-
if (!
|
|
646
|
+
if (!git_fs_path_is_dot_or_dotdotW(findData.cFileName)) {
|
|
641
647
|
empty = false;
|
|
642
648
|
break;
|
|
643
649
|
}
|
|
@@ -651,33 +657,33 @@ bool git_path_is_empty_dir(const char *path)
|
|
|
651
657
|
|
|
652
658
|
#else
|
|
653
659
|
|
|
654
|
-
static int path_found_entry(void *payload,
|
|
660
|
+
static int path_found_entry(void *payload, git_str *path)
|
|
655
661
|
{
|
|
656
662
|
GIT_UNUSED(payload);
|
|
657
|
-
return !
|
|
663
|
+
return !git_fs_path_is_dot_or_dotdot(path->ptr);
|
|
658
664
|
}
|
|
659
665
|
|
|
660
|
-
bool
|
|
666
|
+
bool git_fs_path_is_empty_dir(const char *path)
|
|
661
667
|
{
|
|
662
668
|
int error;
|
|
663
|
-
|
|
669
|
+
git_str dir = GIT_STR_INIT;
|
|
664
670
|
|
|
665
|
-
if (!
|
|
671
|
+
if (!git_fs_path_isdir(path))
|
|
666
672
|
return false;
|
|
667
673
|
|
|
668
|
-
if ((error =
|
|
674
|
+
if ((error = git_str_sets(&dir, path)) != 0)
|
|
669
675
|
git_error_clear();
|
|
670
676
|
else
|
|
671
|
-
error =
|
|
677
|
+
error = git_fs_path_direach(&dir, 0, path_found_entry, NULL);
|
|
672
678
|
|
|
673
|
-
|
|
679
|
+
git_str_dispose(&dir);
|
|
674
680
|
|
|
675
681
|
return !error;
|
|
676
682
|
}
|
|
677
683
|
|
|
678
684
|
#endif
|
|
679
685
|
|
|
680
|
-
int
|
|
686
|
+
int git_fs_path_set_error(int errno_value, const char *path, const char *action)
|
|
681
687
|
{
|
|
682
688
|
switch (errno_value) {
|
|
683
689
|
case ENOENT:
|
|
@@ -704,87 +710,87 @@ int git_path_set_error(int errno_value, const char *path, const char *action)
|
|
|
704
710
|
}
|
|
705
711
|
}
|
|
706
712
|
|
|
707
|
-
int
|
|
713
|
+
int git_fs_path_lstat(const char *path, struct stat *st)
|
|
708
714
|
{
|
|
709
715
|
if (p_lstat(path, st) == 0)
|
|
710
716
|
return 0;
|
|
711
717
|
|
|
712
|
-
return
|
|
718
|
+
return git_fs_path_set_error(errno, path, "stat");
|
|
713
719
|
}
|
|
714
720
|
|
|
715
721
|
static bool _check_dir_contents(
|
|
716
|
-
|
|
722
|
+
git_str *dir,
|
|
717
723
|
const char *sub,
|
|
718
724
|
bool (*predicate)(const char *))
|
|
719
725
|
{
|
|
720
726
|
bool result;
|
|
721
|
-
size_t dir_size =
|
|
727
|
+
size_t dir_size = git_str_len(dir);
|
|
722
728
|
size_t sub_size = strlen(sub);
|
|
723
729
|
size_t alloc_size;
|
|
724
730
|
|
|
725
731
|
/* leave base valid even if we could not make space for subdir */
|
|
726
732
|
if (GIT_ADD_SIZET_OVERFLOW(&alloc_size, dir_size, sub_size) ||
|
|
727
733
|
GIT_ADD_SIZET_OVERFLOW(&alloc_size, alloc_size, 2) ||
|
|
728
|
-
|
|
734
|
+
git_str_try_grow(dir, alloc_size, false) < 0)
|
|
729
735
|
return false;
|
|
730
736
|
|
|
731
737
|
/* save excursion */
|
|
732
|
-
if (
|
|
738
|
+
if (git_str_joinpath(dir, dir->ptr, sub) < 0)
|
|
733
739
|
return false;
|
|
734
740
|
|
|
735
741
|
result = predicate(dir->ptr);
|
|
736
742
|
|
|
737
743
|
/* restore path */
|
|
738
|
-
|
|
744
|
+
git_str_truncate(dir, dir_size);
|
|
739
745
|
return result;
|
|
740
746
|
}
|
|
741
747
|
|
|
742
|
-
bool
|
|
748
|
+
bool git_fs_path_contains(git_str *dir, const char *item)
|
|
743
749
|
{
|
|
744
|
-
return _check_dir_contents(dir, item, &
|
|
750
|
+
return _check_dir_contents(dir, item, &git_fs_path_exists);
|
|
745
751
|
}
|
|
746
752
|
|
|
747
|
-
bool
|
|
753
|
+
bool git_fs_path_contains_dir(git_str *base, const char *subdir)
|
|
748
754
|
{
|
|
749
|
-
return _check_dir_contents(base, subdir, &
|
|
755
|
+
return _check_dir_contents(base, subdir, &git_fs_path_isdir);
|
|
750
756
|
}
|
|
751
757
|
|
|
752
|
-
bool
|
|
758
|
+
bool git_fs_path_contains_file(git_str *base, const char *file)
|
|
753
759
|
{
|
|
754
|
-
return _check_dir_contents(base, file, &
|
|
760
|
+
return _check_dir_contents(base, file, &git_fs_path_isfile);
|
|
755
761
|
}
|
|
756
762
|
|
|
757
|
-
int
|
|
763
|
+
int git_fs_path_find_dir(git_str *dir)
|
|
758
764
|
{
|
|
759
765
|
int error = 0;
|
|
760
766
|
char buf[GIT_PATH_MAX];
|
|
761
767
|
|
|
762
768
|
if (p_realpath(dir->ptr, buf) != NULL)
|
|
763
|
-
error =
|
|
769
|
+
error = git_str_sets(dir, buf);
|
|
764
770
|
|
|
765
771
|
/* call dirname if this is not a directory */
|
|
766
|
-
if (!error) /* &&
|
|
767
|
-
error = (
|
|
772
|
+
if (!error) /* && git_fs_path_isdir(dir->ptr) == false) */
|
|
773
|
+
error = (git_fs_path_dirname_r(dir, dir->ptr) < 0) ? -1 : 0;
|
|
768
774
|
|
|
769
775
|
if (!error)
|
|
770
|
-
error =
|
|
776
|
+
error = git_fs_path_to_dir(dir);
|
|
771
777
|
|
|
772
778
|
return error;
|
|
773
779
|
}
|
|
774
780
|
|
|
775
|
-
int
|
|
781
|
+
int git_fs_path_resolve_relative(git_str *path, size_t ceiling)
|
|
776
782
|
{
|
|
777
783
|
char *base, *to, *from, *next;
|
|
778
784
|
size_t len;
|
|
779
785
|
|
|
780
|
-
|
|
786
|
+
GIT_ERROR_CHECK_ALLOC_STR(path);
|
|
781
787
|
|
|
782
788
|
if (ceiling > path->size)
|
|
783
789
|
ceiling = path->size;
|
|
784
790
|
|
|
785
791
|
/* recognize drive prefixes, etc. that should not be backed over */
|
|
786
792
|
if (ceiling == 0)
|
|
787
|
-
ceiling =
|
|
793
|
+
ceiling = git_fs_path_root(path->ptr) + 1;
|
|
788
794
|
|
|
789
795
|
/* recognize URL prefixes that should not be backed over */
|
|
790
796
|
if (ceiling == 0) {
|
|
@@ -851,13 +857,13 @@ int git_path_resolve_relative(git_buf *path, size_t ceiling)
|
|
|
851
857
|
return 0;
|
|
852
858
|
}
|
|
853
859
|
|
|
854
|
-
int
|
|
860
|
+
int git_fs_path_apply_relative(git_str *target, const char *relpath)
|
|
855
861
|
{
|
|
856
|
-
return
|
|
857
|
-
|
|
862
|
+
return git_str_joinpath(target, git_str_cstr(target), relpath) ||
|
|
863
|
+
git_fs_path_resolve_relative(target, 0);
|
|
858
864
|
}
|
|
859
865
|
|
|
860
|
-
int
|
|
866
|
+
int git_fs_path_cmp(
|
|
861
867
|
const char *name1, size_t len1, int isdir1,
|
|
862
868
|
const char *name2, size_t len2, int isdir2,
|
|
863
869
|
int (*compare)(const char *, const char *, size_t))
|
|
@@ -882,7 +888,7 @@ int git_path_cmp(
|
|
|
882
888
|
return (c1 < c2) ? -1 : (c1 > c2) ? 1 : 0;
|
|
883
889
|
}
|
|
884
890
|
|
|
885
|
-
size_t
|
|
891
|
+
size_t git_fs_path_common_dirlen(const char *one, const char *two)
|
|
886
892
|
{
|
|
887
893
|
const char *p, *q, *dirsep = NULL;
|
|
888
894
|
|
|
@@ -896,7 +902,7 @@ size_t git_path_common_dirlen(const char *one, const char *two)
|
|
|
896
902
|
return dirsep ? (dirsep - one) + 1 : 0;
|
|
897
903
|
}
|
|
898
904
|
|
|
899
|
-
int
|
|
905
|
+
int git_fs_path_make_relative(git_str *path, const char *parent)
|
|
900
906
|
{
|
|
901
907
|
const char *p, *q, *p_dirsep, *q_dirsep;
|
|
902
908
|
size_t plen = path->size, newlen, alloclen, depth = 1, i, offset;
|
|
@@ -923,7 +929,7 @@ int git_path_make_relative(git_buf *path, const char *parent)
|
|
|
923
929
|
else if (!*p && *q == '/')
|
|
924
930
|
q++;
|
|
925
931
|
else if (!*p && !*q)
|
|
926
|
-
return
|
|
932
|
+
return git_str_clear(path), 0;
|
|
927
933
|
else {
|
|
928
934
|
p = p_dirsep + 1;
|
|
929
935
|
q = q_dirsep + 1;
|
|
@@ -932,7 +938,7 @@ int git_path_make_relative(git_buf *path, const char *parent)
|
|
|
932
938
|
plen -= (p - path->ptr);
|
|
933
939
|
|
|
934
940
|
if (!*q)
|
|
935
|
-
return
|
|
941
|
+
return git_str_set(path, p, plen);
|
|
936
942
|
|
|
937
943
|
for (; (q = strchr(q, '/')) && *(q + 1); q++)
|
|
938
944
|
depth++;
|
|
@@ -944,7 +950,7 @@ int git_path_make_relative(git_buf *path, const char *parent)
|
|
|
944
950
|
|
|
945
951
|
/* save the offset as we might realllocate the pointer */
|
|
946
952
|
offset = p - path->ptr;
|
|
947
|
-
if (
|
|
953
|
+
if (git_str_try_grow(path, alloclen, 1) < 0)
|
|
948
954
|
return -1;
|
|
949
955
|
p = path->ptr + offset;
|
|
950
956
|
|
|
@@ -957,7 +963,7 @@ int git_path_make_relative(git_buf *path, const char *parent)
|
|
|
957
963
|
return 0;
|
|
958
964
|
}
|
|
959
965
|
|
|
960
|
-
bool
|
|
966
|
+
bool git_fs_path_has_non_ascii(const char *path, size_t pathlen)
|
|
961
967
|
{
|
|
962
968
|
const uint8_t *scan = (const uint8_t *)path, *end;
|
|
963
969
|
|
|
@@ -970,37 +976,37 @@ bool git_path_has_non_ascii(const char *path, size_t pathlen)
|
|
|
970
976
|
|
|
971
977
|
#ifdef GIT_USE_ICONV
|
|
972
978
|
|
|
973
|
-
int
|
|
979
|
+
int git_fs_path_iconv_init_precompose(git_fs_path_iconv_t *ic)
|
|
974
980
|
{
|
|
975
|
-
|
|
981
|
+
git_str_init(&ic->buf, 0);
|
|
976
982
|
ic->map = iconv_open(GIT_PATH_REPO_ENCODING, GIT_PATH_NATIVE_ENCODING);
|
|
977
983
|
return 0;
|
|
978
984
|
}
|
|
979
985
|
|
|
980
|
-
void
|
|
986
|
+
void git_fs_path_iconv_clear(git_fs_path_iconv_t *ic)
|
|
981
987
|
{
|
|
982
988
|
if (ic) {
|
|
983
989
|
if (ic->map != (iconv_t)-1)
|
|
984
990
|
iconv_close(ic->map);
|
|
985
|
-
|
|
991
|
+
git_str_dispose(&ic->buf);
|
|
986
992
|
}
|
|
987
993
|
}
|
|
988
994
|
|
|
989
|
-
int
|
|
995
|
+
int git_fs_path_iconv(git_fs_path_iconv_t *ic, const char **in, size_t *inlen)
|
|
990
996
|
{
|
|
991
997
|
char *nfd = (char*)*in, *nfc;
|
|
992
998
|
size_t nfdlen = *inlen, nfclen, wantlen = nfdlen, alloclen, rv;
|
|
993
999
|
int retry = 1;
|
|
994
1000
|
|
|
995
1001
|
if (!ic || ic->map == (iconv_t)-1 ||
|
|
996
|
-
!
|
|
1002
|
+
!git_fs_path_has_non_ascii(*in, *inlen))
|
|
997
1003
|
return 0;
|
|
998
1004
|
|
|
999
|
-
|
|
1005
|
+
git_str_clear(&ic->buf);
|
|
1000
1006
|
|
|
1001
1007
|
while (1) {
|
|
1002
1008
|
GIT_ERROR_CHECK_ALLOC_ADD(&alloclen, wantlen, 1);
|
|
1003
|
-
if (
|
|
1009
|
+
if (git_str_grow(&ic->buf, alloclen) < 0)
|
|
1004
1010
|
return -1;
|
|
1005
1011
|
|
|
1006
1012
|
nfc = ic->buf.ptr + ic->buf.size;
|
|
@@ -1040,8 +1046,8 @@ fail:
|
|
|
1040
1046
|
return -1;
|
|
1041
1047
|
}
|
|
1042
1048
|
|
|
1043
|
-
static const char *nfc_file = "\xC3\x85\x73\x74\x72\xC3\xB6\x6D
|
|
1044
|
-
static const char *nfd_file = "\x41\xCC\x8A\x73\x74\x72\x6F\xCC\x88\x6D
|
|
1049
|
+
static const char *nfc_file = "\xC3\x85\x73\x74\x72\xC3\xB6\x6D";
|
|
1050
|
+
static const char *nfd_file = "\x41\xCC\x8A\x73\x74\x72\x6F\xCC\x88\x6D";
|
|
1045
1051
|
|
|
1046
1052
|
/* Check if the platform is decomposing unicode data for us. We will
|
|
1047
1053
|
* emulate core Git and prefer to use precomposed unicode data internally
|
|
@@ -1052,47 +1058,50 @@ static const char *nfd_file = "\x41\xCC\x8A\x73\x74\x72\x6F\xCC\x88\x6D.XXXXXX";
|
|
|
1052
1058
|
* return decomposed unicode from readdir() even when the actual
|
|
1053
1059
|
* filesystem is storing precomposed unicode.
|
|
1054
1060
|
*/
|
|
1055
|
-
bool
|
|
1061
|
+
bool git_fs_path_does_decompose_unicode(const char *root)
|
|
1056
1062
|
{
|
|
1057
|
-
|
|
1063
|
+
git_str nfc_path = GIT_STR_INIT;
|
|
1064
|
+
git_str nfd_path = GIT_STR_INIT;
|
|
1058
1065
|
int fd;
|
|
1059
1066
|
bool found_decomposed = false;
|
|
1060
|
-
|
|
1067
|
+
size_t orig_len;
|
|
1068
|
+
const char *trailer;
|
|
1061
1069
|
|
|
1062
1070
|
/* Create a file using a precomposed path and then try to find it
|
|
1063
1071
|
* using the decomposed name. If the lookup fails, then we will mark
|
|
1064
1072
|
* that we should precompose unicode for this repository.
|
|
1065
1073
|
*/
|
|
1066
|
-
if (
|
|
1067
|
-
|
|
1074
|
+
if (git_str_joinpath(&nfc_path, root, nfc_file) < 0)
|
|
1075
|
+
goto done;
|
|
1076
|
+
|
|
1077
|
+
/* record original path length before trailer */
|
|
1078
|
+
orig_len = nfc_path.size;
|
|
1079
|
+
|
|
1080
|
+
if ((fd = git_futils_mktmp(&nfc_path, nfc_path.ptr, 0666)) < 0)
|
|
1068
1081
|
goto done;
|
|
1069
1082
|
p_close(fd);
|
|
1070
1083
|
|
|
1071
|
-
|
|
1072
|
-
memcpy(tmp, path.ptr + path.size - sizeof(tmp), sizeof(tmp));
|
|
1084
|
+
trailer = nfc_path.ptr + orig_len;
|
|
1073
1085
|
|
|
1074
1086
|
/* try to look up as NFD path */
|
|
1075
|
-
if (
|
|
1087
|
+
if (git_str_joinpath(&nfd_path, root, nfd_file) < 0 ||
|
|
1088
|
+
git_str_puts(&nfd_path, trailer) < 0)
|
|
1076
1089
|
goto done;
|
|
1077
|
-
memcpy(path.ptr + path.size - sizeof(tmp), tmp, sizeof(tmp));
|
|
1078
1090
|
|
|
1079
|
-
found_decomposed =
|
|
1091
|
+
found_decomposed = git_fs_path_exists(nfd_path.ptr);
|
|
1080
1092
|
|
|
1081
1093
|
/* remove temporary file (using original precomposed path) */
|
|
1082
|
-
|
|
1083
|
-
goto done;
|
|
1084
|
-
memcpy(path.ptr + path.size - sizeof(tmp), tmp, sizeof(tmp));
|
|
1085
|
-
|
|
1086
|
-
(void)p_unlink(path.ptr);
|
|
1094
|
+
(void)p_unlink(nfc_path.ptr);
|
|
1087
1095
|
|
|
1088
1096
|
done:
|
|
1089
|
-
|
|
1097
|
+
git_str_dispose(&nfc_path);
|
|
1098
|
+
git_str_dispose(&nfd_path);
|
|
1090
1099
|
return found_decomposed;
|
|
1091
1100
|
}
|
|
1092
1101
|
|
|
1093
1102
|
#else
|
|
1094
1103
|
|
|
1095
|
-
bool
|
|
1104
|
+
bool git_fs_path_does_decompose_unicode(const char *root)
|
|
1096
1105
|
{
|
|
1097
1106
|
GIT_UNUSED(root);
|
|
1098
1107
|
return false;
|
|
@@ -1106,10 +1115,10 @@ typedef char path_dirent_data[sizeof(struct dirent) + FILENAME_MAX + 1];
|
|
|
1106
1115
|
typedef struct dirent path_dirent_data;
|
|
1107
1116
|
#endif
|
|
1108
1117
|
|
|
1109
|
-
int
|
|
1110
|
-
|
|
1118
|
+
int git_fs_path_direach(
|
|
1119
|
+
git_str *path,
|
|
1111
1120
|
uint32_t flags,
|
|
1112
|
-
int (*fn)(void *,
|
|
1121
|
+
int (*fn)(void *, git_str *),
|
|
1113
1122
|
void *arg)
|
|
1114
1123
|
{
|
|
1115
1124
|
int error = 0;
|
|
@@ -1118,15 +1127,15 @@ int git_path_direach(
|
|
|
1118
1127
|
struct dirent *de;
|
|
1119
1128
|
|
|
1120
1129
|
#ifdef GIT_USE_ICONV
|
|
1121
|
-
|
|
1130
|
+
git_fs_path_iconv_t ic = GIT_PATH_ICONV_INIT;
|
|
1122
1131
|
#endif
|
|
1123
1132
|
|
|
1124
1133
|
GIT_UNUSED(flags);
|
|
1125
1134
|
|
|
1126
|
-
if (
|
|
1135
|
+
if (git_fs_path_to_dir(path) < 0)
|
|
1127
1136
|
return -1;
|
|
1128
1137
|
|
|
1129
|
-
wd_len =
|
|
1138
|
+
wd_len = git_str_len(path);
|
|
1130
1139
|
|
|
1131
1140
|
if ((dir = opendir(path->ptr)) == NULL) {
|
|
1132
1141
|
git_error_set(GIT_ERROR_OS, "failed to open directory '%s'", path->ptr);
|
|
@@ -1137,34 +1146,34 @@ int git_path_direach(
|
|
|
1137
1146
|
}
|
|
1138
1147
|
|
|
1139
1148
|
#ifdef GIT_USE_ICONV
|
|
1140
|
-
if ((flags &
|
|
1141
|
-
(void)
|
|
1149
|
+
if ((flags & GIT_FS_PATH_DIR_PRECOMPOSE_UNICODE) != 0)
|
|
1150
|
+
(void)git_fs_path_iconv_init_precompose(&ic);
|
|
1142
1151
|
#endif
|
|
1143
1152
|
|
|
1144
1153
|
while ((de = readdir(dir)) != NULL) {
|
|
1145
1154
|
const char *de_path = de->d_name;
|
|
1146
1155
|
size_t de_len = strlen(de_path);
|
|
1147
1156
|
|
|
1148
|
-
if (
|
|
1157
|
+
if (git_fs_path_is_dot_or_dotdot(de_path))
|
|
1149
1158
|
continue;
|
|
1150
1159
|
|
|
1151
1160
|
#ifdef GIT_USE_ICONV
|
|
1152
|
-
if ((error =
|
|
1161
|
+
if ((error = git_fs_path_iconv(&ic, &de_path, &de_len)) < 0)
|
|
1153
1162
|
break;
|
|
1154
1163
|
#endif
|
|
1155
1164
|
|
|
1156
|
-
if ((error =
|
|
1165
|
+
if ((error = git_str_put(path, de_path, de_len)) < 0)
|
|
1157
1166
|
break;
|
|
1158
1167
|
|
|
1159
1168
|
git_error_clear();
|
|
1160
1169
|
error = fn(arg, path);
|
|
1161
1170
|
|
|
1162
|
-
|
|
1171
|
+
git_str_truncate(path, wd_len); /* restore path */
|
|
1163
1172
|
|
|
1164
1173
|
/* Only set our own error if the callback did not set one already */
|
|
1165
1174
|
if (error != 0) {
|
|
1166
1175
|
if (!git_error_last())
|
|
1167
|
-
|
|
1176
|
+
ensure_error_set(error);
|
|
1168
1177
|
|
|
1169
1178
|
break;
|
|
1170
1179
|
}
|
|
@@ -1173,7 +1182,7 @@ int git_path_direach(
|
|
|
1173
1182
|
closedir(dir);
|
|
1174
1183
|
|
|
1175
1184
|
#ifdef GIT_USE_ICONV
|
|
1176
|
-
|
|
1185
|
+
git_fs_path_iconv_clear(&ic);
|
|
1177
1186
|
#endif
|
|
1178
1187
|
|
|
1179
1188
|
return error;
|
|
@@ -1188,8 +1197,8 @@ int git_path_direach(
|
|
|
1188
1197
|
# define FIND_FIRST_EX_LARGE_FETCH 2
|
|
1189
1198
|
#endif
|
|
1190
1199
|
|
|
1191
|
-
int
|
|
1192
|
-
|
|
1200
|
+
int git_fs_path_diriter_init(
|
|
1201
|
+
git_fs_path_diriter *diriter,
|
|
1193
1202
|
const char *path,
|
|
1194
1203
|
unsigned int flags)
|
|
1195
1204
|
{
|
|
@@ -1202,10 +1211,10 @@ int git_path_diriter_init(
|
|
|
1202
1211
|
GIT_ASSERT_ARG(diriter);
|
|
1203
1212
|
GIT_ASSERT_ARG(path);
|
|
1204
1213
|
|
|
1205
|
-
memset(diriter, 0, sizeof(
|
|
1214
|
+
memset(diriter, 0, sizeof(git_fs_path_diriter));
|
|
1206
1215
|
diriter->handle = INVALID_HANDLE_VALUE;
|
|
1207
1216
|
|
|
1208
|
-
if (
|
|
1217
|
+
if (git_str_puts(&diriter->path_utf8, path) < 0)
|
|
1209
1218
|
return -1;
|
|
1210
1219
|
|
|
1211
1220
|
path_trim_slashes(&diriter->path_utf8);
|
|
@@ -1239,7 +1248,7 @@ int git_path_diriter_init(
|
|
|
1239
1248
|
return 0;
|
|
1240
1249
|
}
|
|
1241
1250
|
|
|
1242
|
-
static int diriter_update_paths(
|
|
1251
|
+
static int diriter_update_paths(git_fs_path_diriter *diriter)
|
|
1243
1252
|
{
|
|
1244
1253
|
size_t filename_len, path_len;
|
|
1245
1254
|
|
|
@@ -1261,23 +1270,23 @@ static int diriter_update_paths(git_path_diriter *diriter)
|
|
|
1261
1270
|
diriter->current.cFileName, filename_len * sizeof(wchar_t));
|
|
1262
1271
|
diriter->path[path_len-1] = L'\0';
|
|
1263
1272
|
|
|
1264
|
-
|
|
1273
|
+
git_str_truncate(&diriter->path_utf8, diriter->parent_utf8_len);
|
|
1265
1274
|
|
|
1266
1275
|
if (diriter->parent_utf8_len > 0 &&
|
|
1267
1276
|
diriter->path_utf8.ptr[diriter->parent_utf8_len-1] != '/')
|
|
1268
|
-
|
|
1277
|
+
git_str_putc(&diriter->path_utf8, '/');
|
|
1269
1278
|
|
|
1270
|
-
|
|
1279
|
+
git_str_put_w(&diriter->path_utf8, diriter->current.cFileName, filename_len);
|
|
1271
1280
|
|
|
1272
|
-
if (
|
|
1281
|
+
if (git_str_oom(&diriter->path_utf8))
|
|
1273
1282
|
return -1;
|
|
1274
1283
|
|
|
1275
1284
|
return 0;
|
|
1276
1285
|
}
|
|
1277
1286
|
|
|
1278
|
-
int
|
|
1287
|
+
int git_fs_path_diriter_next(git_fs_path_diriter *diriter)
|
|
1279
1288
|
{
|
|
1280
|
-
bool skip_dot = !(diriter->flags &
|
|
1289
|
+
bool skip_dot = !(diriter->flags & GIT_FS_PATH_DIR_INCLUDE_DOT_AND_DOTDOT);
|
|
1281
1290
|
|
|
1282
1291
|
do {
|
|
1283
1292
|
/* Our first time through, we already have the data from
|
|
@@ -1287,7 +1296,7 @@ int git_path_diriter_next(git_path_diriter *diriter)
|
|
|
1287
1296
|
diriter->needs_next = 1;
|
|
1288
1297
|
else if (!FindNextFileW(diriter->handle, &diriter->current))
|
|
1289
1298
|
return GIT_ITEROVER;
|
|
1290
|
-
} while (skip_dot &&
|
|
1299
|
+
} while (skip_dot && git_fs_path_is_dot_or_dotdotW(diriter->current.cFileName));
|
|
1291
1300
|
|
|
1292
1301
|
if (diriter_update_paths(diriter) < 0)
|
|
1293
1302
|
return -1;
|
|
@@ -1295,10 +1304,10 @@ int git_path_diriter_next(git_path_diriter *diriter)
|
|
|
1295
1304
|
return 0;
|
|
1296
1305
|
}
|
|
1297
1306
|
|
|
1298
|
-
int
|
|
1307
|
+
int git_fs_path_diriter_filename(
|
|
1299
1308
|
const char **out,
|
|
1300
1309
|
size_t *out_len,
|
|
1301
|
-
|
|
1310
|
+
git_fs_path_diriter *diriter)
|
|
1302
1311
|
{
|
|
1303
1312
|
GIT_ASSERT_ARG(out);
|
|
1304
1313
|
GIT_ASSERT_ARG(out_len);
|
|
@@ -1310,10 +1319,10 @@ int git_path_diriter_filename(
|
|
|
1310
1319
|
return 0;
|
|
1311
1320
|
}
|
|
1312
1321
|
|
|
1313
|
-
int
|
|
1322
|
+
int git_fs_path_diriter_fullpath(
|
|
1314
1323
|
const char **out,
|
|
1315
1324
|
size_t *out_len,
|
|
1316
|
-
|
|
1325
|
+
git_fs_path_diriter *diriter)
|
|
1317
1326
|
{
|
|
1318
1327
|
GIT_ASSERT_ARG(out);
|
|
1319
1328
|
GIT_ASSERT_ARG(out_len);
|
|
@@ -1324,7 +1333,7 @@ int git_path_diriter_fullpath(
|
|
|
1324
1333
|
return 0;
|
|
1325
1334
|
}
|
|
1326
1335
|
|
|
1327
|
-
int
|
|
1336
|
+
int git_fs_path_diriter_stat(struct stat *out, git_fs_path_diriter *diriter)
|
|
1328
1337
|
{
|
|
1329
1338
|
GIT_ASSERT_ARG(out);
|
|
1330
1339
|
GIT_ASSERT_ARG(diriter);
|
|
@@ -1334,12 +1343,12 @@ int git_path_diriter_stat(struct stat *out, git_path_diriter *diriter)
|
|
|
1334
1343
|
diriter->path);
|
|
1335
1344
|
}
|
|
1336
1345
|
|
|
1337
|
-
void
|
|
1346
|
+
void git_fs_path_diriter_free(git_fs_path_diriter *diriter)
|
|
1338
1347
|
{
|
|
1339
1348
|
if (diriter == NULL)
|
|
1340
1349
|
return;
|
|
1341
1350
|
|
|
1342
|
-
|
|
1351
|
+
git_str_dispose(&diriter->path_utf8);
|
|
1343
1352
|
|
|
1344
1353
|
if (diriter->handle != INVALID_HANDLE_VALUE) {
|
|
1345
1354
|
FindClose(diriter->handle);
|
|
@@ -1349,17 +1358,17 @@ void git_path_diriter_free(git_path_diriter *diriter)
|
|
|
1349
1358
|
|
|
1350
1359
|
#else
|
|
1351
1360
|
|
|
1352
|
-
int
|
|
1353
|
-
|
|
1361
|
+
int git_fs_path_diriter_init(
|
|
1362
|
+
git_fs_path_diriter *diriter,
|
|
1354
1363
|
const char *path,
|
|
1355
1364
|
unsigned int flags)
|
|
1356
1365
|
{
|
|
1357
1366
|
GIT_ASSERT_ARG(diriter);
|
|
1358
1367
|
GIT_ASSERT_ARG(path);
|
|
1359
1368
|
|
|
1360
|
-
memset(diriter, 0, sizeof(
|
|
1369
|
+
memset(diriter, 0, sizeof(git_fs_path_diriter));
|
|
1361
1370
|
|
|
1362
|
-
if (
|
|
1371
|
+
if (git_str_puts(&diriter->path, path) < 0)
|
|
1363
1372
|
return -1;
|
|
1364
1373
|
|
|
1365
1374
|
path_trim_slashes(&diriter->path);
|
|
@@ -1370,15 +1379,15 @@ int git_path_diriter_init(
|
|
|
1370
1379
|
}
|
|
1371
1380
|
|
|
1372
1381
|
if ((diriter->dir = opendir(diriter->path.ptr)) == NULL) {
|
|
1373
|
-
|
|
1382
|
+
git_str_dispose(&diriter->path);
|
|
1374
1383
|
|
|
1375
1384
|
git_error_set(GIT_ERROR_OS, "failed to open directory '%s'", path);
|
|
1376
1385
|
return -1;
|
|
1377
1386
|
}
|
|
1378
1387
|
|
|
1379
1388
|
#ifdef GIT_USE_ICONV
|
|
1380
|
-
if ((flags &
|
|
1381
|
-
(void)
|
|
1389
|
+
if ((flags & GIT_FS_PATH_DIR_PRECOMPOSE_UNICODE) != 0)
|
|
1390
|
+
(void)git_fs_path_iconv_init_precompose(&diriter->ic);
|
|
1382
1391
|
#endif
|
|
1383
1392
|
|
|
1384
1393
|
diriter->parent_len = diriter->path.size;
|
|
@@ -1387,12 +1396,12 @@ int git_path_diriter_init(
|
|
|
1387
1396
|
return 0;
|
|
1388
1397
|
}
|
|
1389
1398
|
|
|
1390
|
-
int
|
|
1399
|
+
int git_fs_path_diriter_next(git_fs_path_diriter *diriter)
|
|
1391
1400
|
{
|
|
1392
1401
|
struct dirent *de;
|
|
1393
1402
|
const char *filename;
|
|
1394
1403
|
size_t filename_len;
|
|
1395
|
-
bool skip_dot = !(diriter->flags &
|
|
1404
|
+
bool skip_dot = !(diriter->flags & GIT_FS_PATH_DIR_INCLUDE_DOT_AND_DOTDOT);
|
|
1396
1405
|
int error = 0;
|
|
1397
1406
|
|
|
1398
1407
|
GIT_ASSERT_ARG(diriter);
|
|
@@ -1408,35 +1417,35 @@ int git_path_diriter_next(git_path_diriter *diriter)
|
|
|
1408
1417
|
"could not read directory '%s'", diriter->path.ptr);
|
|
1409
1418
|
return -1;
|
|
1410
1419
|
}
|
|
1411
|
-
} while (skip_dot &&
|
|
1420
|
+
} while (skip_dot && git_fs_path_is_dot_or_dotdot(de->d_name));
|
|
1412
1421
|
|
|
1413
1422
|
filename = de->d_name;
|
|
1414
1423
|
filename_len = strlen(filename);
|
|
1415
1424
|
|
|
1416
1425
|
#ifdef GIT_USE_ICONV
|
|
1417
|
-
if ((diriter->flags &
|
|
1418
|
-
(error =
|
|
1426
|
+
if ((diriter->flags & GIT_FS_PATH_DIR_PRECOMPOSE_UNICODE) != 0 &&
|
|
1427
|
+
(error = git_fs_path_iconv(&diriter->ic, &filename, &filename_len)) < 0)
|
|
1419
1428
|
return error;
|
|
1420
1429
|
#endif
|
|
1421
1430
|
|
|
1422
|
-
|
|
1431
|
+
git_str_truncate(&diriter->path, diriter->parent_len);
|
|
1423
1432
|
|
|
1424
1433
|
if (diriter->parent_len > 0 &&
|
|
1425
1434
|
diriter->path.ptr[diriter->parent_len-1] != '/')
|
|
1426
|
-
|
|
1435
|
+
git_str_putc(&diriter->path, '/');
|
|
1427
1436
|
|
|
1428
|
-
|
|
1437
|
+
git_str_put(&diriter->path, filename, filename_len);
|
|
1429
1438
|
|
|
1430
|
-
if (
|
|
1439
|
+
if (git_str_oom(&diriter->path))
|
|
1431
1440
|
return -1;
|
|
1432
1441
|
|
|
1433
1442
|
return error;
|
|
1434
1443
|
}
|
|
1435
1444
|
|
|
1436
|
-
int
|
|
1445
|
+
int git_fs_path_diriter_filename(
|
|
1437
1446
|
const char **out,
|
|
1438
1447
|
size_t *out_len,
|
|
1439
|
-
|
|
1448
|
+
git_fs_path_diriter *diriter)
|
|
1440
1449
|
{
|
|
1441
1450
|
GIT_ASSERT_ARG(out);
|
|
1442
1451
|
GIT_ASSERT_ARG(out_len);
|
|
@@ -1448,10 +1457,10 @@ int git_path_diriter_filename(
|
|
|
1448
1457
|
return 0;
|
|
1449
1458
|
}
|
|
1450
1459
|
|
|
1451
|
-
int
|
|
1460
|
+
int git_fs_path_diriter_fullpath(
|
|
1452
1461
|
const char **out,
|
|
1453
1462
|
size_t *out_len,
|
|
1454
|
-
|
|
1463
|
+
git_fs_path_diriter *diriter)
|
|
1455
1464
|
{
|
|
1456
1465
|
GIT_ASSERT_ARG(out);
|
|
1457
1466
|
GIT_ASSERT_ARG(out_len);
|
|
@@ -1462,15 +1471,15 @@ int git_path_diriter_fullpath(
|
|
|
1462
1471
|
return 0;
|
|
1463
1472
|
}
|
|
1464
1473
|
|
|
1465
|
-
int
|
|
1474
|
+
int git_fs_path_diriter_stat(struct stat *out, git_fs_path_diriter *diriter)
|
|
1466
1475
|
{
|
|
1467
1476
|
GIT_ASSERT_ARG(out);
|
|
1468
1477
|
GIT_ASSERT_ARG(diriter);
|
|
1469
1478
|
|
|
1470
|
-
return
|
|
1479
|
+
return git_fs_path_lstat(diriter->path.ptr, out);
|
|
1471
1480
|
}
|
|
1472
1481
|
|
|
1473
|
-
void
|
|
1482
|
+
void git_fs_path_diriter_free(git_fs_path_diriter *diriter)
|
|
1474
1483
|
{
|
|
1475
1484
|
if (diriter == NULL)
|
|
1476
1485
|
return;
|
|
@@ -1481,21 +1490,21 @@ void git_path_diriter_free(git_path_diriter *diriter)
|
|
|
1481
1490
|
}
|
|
1482
1491
|
|
|
1483
1492
|
#ifdef GIT_USE_ICONV
|
|
1484
|
-
|
|
1493
|
+
git_fs_path_iconv_clear(&diriter->ic);
|
|
1485
1494
|
#endif
|
|
1486
1495
|
|
|
1487
|
-
|
|
1496
|
+
git_str_dispose(&diriter->path);
|
|
1488
1497
|
}
|
|
1489
1498
|
|
|
1490
1499
|
#endif
|
|
1491
1500
|
|
|
1492
|
-
int
|
|
1501
|
+
int git_fs_path_dirload(
|
|
1493
1502
|
git_vector *contents,
|
|
1494
1503
|
const char *path,
|
|
1495
1504
|
size_t prefix_len,
|
|
1496
1505
|
uint32_t flags)
|
|
1497
1506
|
{
|
|
1498
|
-
|
|
1507
|
+
git_fs_path_diriter iter = GIT_FS_PATH_DIRITER_INIT;
|
|
1499
1508
|
const char *name;
|
|
1500
1509
|
size_t name_len;
|
|
1501
1510
|
char *dup;
|
|
@@ -1504,11 +1513,11 @@ int git_path_dirload(
|
|
|
1504
1513
|
GIT_ASSERT_ARG(contents);
|
|
1505
1514
|
GIT_ASSERT_ARG(path);
|
|
1506
1515
|
|
|
1507
|
-
if ((error =
|
|
1516
|
+
if ((error = git_fs_path_diriter_init(&iter, path, flags)) < 0)
|
|
1508
1517
|
return error;
|
|
1509
1518
|
|
|
1510
|
-
while ((error =
|
|
1511
|
-
if ((error =
|
|
1519
|
+
while ((error = git_fs_path_diriter_next(&iter)) == 0) {
|
|
1520
|
+
if ((error = git_fs_path_diriter_fullpath(&name, &name_len, &iter)) < 0)
|
|
1512
1521
|
break;
|
|
1513
1522
|
|
|
1514
1523
|
GIT_ASSERT(name_len > prefix_len);
|
|
@@ -1523,22 +1532,22 @@ int git_path_dirload(
|
|
|
1523
1532
|
if (error == GIT_ITEROVER)
|
|
1524
1533
|
error = 0;
|
|
1525
1534
|
|
|
1526
|
-
|
|
1535
|
+
git_fs_path_diriter_free(&iter);
|
|
1527
1536
|
return error;
|
|
1528
1537
|
}
|
|
1529
1538
|
|
|
1530
|
-
int
|
|
1539
|
+
int git_fs_path_from_url_or_path(git_str *local_path_out, const char *url_or_path)
|
|
1531
1540
|
{
|
|
1532
|
-
if (
|
|
1533
|
-
return
|
|
1541
|
+
if (git_fs_path_is_local_file_url(url_or_path))
|
|
1542
|
+
return git_fs_path_fromurl(local_path_out, url_or_path);
|
|
1534
1543
|
else
|
|
1535
|
-
return
|
|
1544
|
+
return git_str_sets(local_path_out, url_or_path);
|
|
1536
1545
|
}
|
|
1537
1546
|
|
|
1538
1547
|
/* Reject paths like AUX or COM1, or those versions that end in a dot or
|
|
1539
1548
|
* colon. ("AUX." or "AUX:")
|
|
1540
1549
|
*/
|
|
1541
|
-
GIT_INLINE(bool)
|
|
1550
|
+
GIT_INLINE(bool) validate_dospath(
|
|
1542
1551
|
const char *component,
|
|
1543
1552
|
size_t len,
|
|
1544
1553
|
const char dospath[3],
|
|
@@ -1557,180 +1566,15 @@ GIT_INLINE(bool) verify_dospath(
|
|
|
1557
1566
|
component[last] != ':');
|
|
1558
1567
|
}
|
|
1559
1568
|
|
|
1560
|
-
|
|
1561
|
-
{
|
|
1562
|
-
while (*len) {
|
|
1563
|
-
uint32_t codepoint;
|
|
1564
|
-
int cp_len = git_utf8_iterate(&codepoint, *in, *len);
|
|
1565
|
-
if (cp_len < 0)
|
|
1566
|
-
return -1;
|
|
1567
|
-
|
|
1568
|
-
(*in) += cp_len;
|
|
1569
|
-
(*len) -= cp_len;
|
|
1570
|
-
|
|
1571
|
-
/* these code points are ignored completely */
|
|
1572
|
-
switch (codepoint) {
|
|
1573
|
-
case 0x200c: /* ZERO WIDTH NON-JOINER */
|
|
1574
|
-
case 0x200d: /* ZERO WIDTH JOINER */
|
|
1575
|
-
case 0x200e: /* LEFT-TO-RIGHT MARK */
|
|
1576
|
-
case 0x200f: /* RIGHT-TO-LEFT MARK */
|
|
1577
|
-
case 0x202a: /* LEFT-TO-RIGHT EMBEDDING */
|
|
1578
|
-
case 0x202b: /* RIGHT-TO-LEFT EMBEDDING */
|
|
1579
|
-
case 0x202c: /* POP DIRECTIONAL FORMATTING */
|
|
1580
|
-
case 0x202d: /* LEFT-TO-RIGHT OVERRIDE */
|
|
1581
|
-
case 0x202e: /* RIGHT-TO-LEFT OVERRIDE */
|
|
1582
|
-
case 0x206a: /* INHIBIT SYMMETRIC SWAPPING */
|
|
1583
|
-
case 0x206b: /* ACTIVATE SYMMETRIC SWAPPING */
|
|
1584
|
-
case 0x206c: /* INHIBIT ARABIC FORM SHAPING */
|
|
1585
|
-
case 0x206d: /* ACTIVATE ARABIC FORM SHAPING */
|
|
1586
|
-
case 0x206e: /* NATIONAL DIGIT SHAPES */
|
|
1587
|
-
case 0x206f: /* NOMINAL DIGIT SHAPES */
|
|
1588
|
-
case 0xfeff: /* ZERO WIDTH NO-BREAK SPACE */
|
|
1589
|
-
continue;
|
|
1590
|
-
}
|
|
1591
|
-
|
|
1592
|
-
/* fold into lowercase -- this will only fold characters in
|
|
1593
|
-
* the ASCII range, which is perfectly fine, because the
|
|
1594
|
-
* git folder name can only be composed of ascii characters
|
|
1595
|
-
*/
|
|
1596
|
-
return git__tolower((int)codepoint);
|
|
1597
|
-
}
|
|
1598
|
-
return 0; /* NULL byte -- end of string */
|
|
1599
|
-
}
|
|
1600
|
-
|
|
1601
|
-
static bool verify_dotgit_hfs_generic(const char *path, size_t len, const char *needle, size_t needle_len)
|
|
1602
|
-
{
|
|
1603
|
-
size_t i;
|
|
1604
|
-
char c;
|
|
1605
|
-
|
|
1606
|
-
if (next_hfs_char(&path, &len) != '.')
|
|
1607
|
-
return true;
|
|
1608
|
-
|
|
1609
|
-
for (i = 0; i < needle_len; i++) {
|
|
1610
|
-
c = next_hfs_char(&path, &len);
|
|
1611
|
-
if (c != needle[i])
|
|
1612
|
-
return true;
|
|
1613
|
-
}
|
|
1614
|
-
|
|
1615
|
-
if (next_hfs_char(&path, &len) != '\0')
|
|
1616
|
-
return true;
|
|
1617
|
-
|
|
1618
|
-
return false;
|
|
1619
|
-
}
|
|
1620
|
-
|
|
1621
|
-
static bool verify_dotgit_hfs(const char *path, size_t len)
|
|
1569
|
+
GIT_INLINE(bool) validate_char(unsigned char c, unsigned int flags)
|
|
1622
1570
|
{
|
|
1623
|
-
|
|
1624
|
-
}
|
|
1625
|
-
|
|
1626
|
-
GIT_INLINE(bool) verify_dotgit_ntfs(git_repository *repo, const char *path, size_t len)
|
|
1627
|
-
{
|
|
1628
|
-
git_buf *reserved = git_repository__reserved_names_win32;
|
|
1629
|
-
size_t reserved_len = git_repository__reserved_names_win32_len;
|
|
1630
|
-
size_t start = 0, i;
|
|
1631
|
-
|
|
1632
|
-
if (repo)
|
|
1633
|
-
git_repository__reserved_names(&reserved, &reserved_len, repo, true);
|
|
1634
|
-
|
|
1635
|
-
for (i = 0; i < reserved_len; i++) {
|
|
1636
|
-
git_buf *r = &reserved[i];
|
|
1637
|
-
|
|
1638
|
-
if (len >= r->size &&
|
|
1639
|
-
strncasecmp(path, r->ptr, r->size) == 0) {
|
|
1640
|
-
start = r->size;
|
|
1641
|
-
break;
|
|
1642
|
-
}
|
|
1643
|
-
}
|
|
1644
|
-
|
|
1645
|
-
if (!start)
|
|
1646
|
-
return true;
|
|
1647
|
-
|
|
1648
|
-
/*
|
|
1649
|
-
* Reject paths that start with Windows-style directory separators
|
|
1650
|
-
* (".git\") or NTFS alternate streams (".git:") and could be used
|
|
1651
|
-
* to write to the ".git" directory on Windows platforms.
|
|
1652
|
-
*/
|
|
1653
|
-
if (path[start] == '\\' || path[start] == ':')
|
|
1571
|
+
if ((flags & GIT_FS_PATH_REJECT_BACKSLASH) && c == '\\')
|
|
1654
1572
|
return false;
|
|
1655
1573
|
|
|
1656
|
-
|
|
1657
|
-
for (i = start; i < len; i++) {
|
|
1658
|
-
if (path[i] != ' ' && path[i] != '.')
|
|
1659
|
-
return true;
|
|
1660
|
-
}
|
|
1661
|
-
|
|
1662
|
-
return false;
|
|
1663
|
-
}
|
|
1664
|
-
|
|
1665
|
-
/*
|
|
1666
|
-
* Windows paths that end with spaces and/or dots are elided to the
|
|
1667
|
-
* path without them for backward compatibility. That is to say
|
|
1668
|
-
* that opening file "foo ", "foo." or even "foo . . ." will all
|
|
1669
|
-
* map to a filename of "foo". This function identifies spaces and
|
|
1670
|
-
* dots at the end of a filename, whether the proper end of the
|
|
1671
|
-
* filename (end of string) or a colon (which would indicate a
|
|
1672
|
-
* Windows alternate data stream.)
|
|
1673
|
-
*/
|
|
1674
|
-
GIT_INLINE(bool) ntfs_end_of_filename(const char *path)
|
|
1675
|
-
{
|
|
1676
|
-
const char *c = path;
|
|
1677
|
-
|
|
1678
|
-
for (;; c++) {
|
|
1679
|
-
if (*c == '\0' || *c == ':')
|
|
1680
|
-
return true;
|
|
1681
|
-
if (*c != ' ' && *c != '.')
|
|
1682
|
-
return false;
|
|
1683
|
-
}
|
|
1684
|
-
|
|
1685
|
-
return true;
|
|
1686
|
-
}
|
|
1687
|
-
|
|
1688
|
-
GIT_INLINE(bool) verify_dotgit_ntfs_generic(const char *name, size_t len, const char *dotgit_name, size_t dotgit_len, const char *shortname_pfix)
|
|
1689
|
-
{
|
|
1690
|
-
int i, saw_tilde;
|
|
1691
|
-
|
|
1692
|
-
if (name[0] == '.' && len >= dotgit_len &&
|
|
1693
|
-
!strncasecmp(name + 1, dotgit_name, dotgit_len)) {
|
|
1694
|
-
return !ntfs_end_of_filename(name + dotgit_len + 1);
|
|
1695
|
-
}
|
|
1696
|
-
|
|
1697
|
-
/* Detect the basic NTFS shortname with the first six chars */
|
|
1698
|
-
if (!strncasecmp(name, dotgit_name, 6) && name[6] == '~' &&
|
|
1699
|
-
name[7] >= '1' && name[7] <= '4')
|
|
1700
|
-
return !ntfs_end_of_filename(name + 8);
|
|
1701
|
-
|
|
1702
|
-
/* Catch fallback names */
|
|
1703
|
-
for (i = 0, saw_tilde = 0; i < 8; i++) {
|
|
1704
|
-
if (name[i] == '\0') {
|
|
1705
|
-
return true;
|
|
1706
|
-
} else if (saw_tilde) {
|
|
1707
|
-
if (name[i] < '0' || name[i] > '9')
|
|
1708
|
-
return true;
|
|
1709
|
-
} else if (name[i] == '~') {
|
|
1710
|
-
if (name[i+1] < '1' || name[i+1] > '9')
|
|
1711
|
-
return true;
|
|
1712
|
-
saw_tilde = 1;
|
|
1713
|
-
} else if (i >= 6) {
|
|
1714
|
-
return true;
|
|
1715
|
-
} else if ((unsigned char)name[i] > 127) {
|
|
1716
|
-
return true;
|
|
1717
|
-
} else if (git__tolower(name[i]) != shortname_pfix[i]) {
|
|
1718
|
-
return true;
|
|
1719
|
-
}
|
|
1720
|
-
}
|
|
1721
|
-
|
|
1722
|
-
return !ntfs_end_of_filename(name + i);
|
|
1723
|
-
}
|
|
1724
|
-
|
|
1725
|
-
GIT_INLINE(bool) verify_char(unsigned char c, unsigned int flags)
|
|
1726
|
-
{
|
|
1727
|
-
if ((flags & GIT_PATH_REJECT_BACKSLASH) && c == '\\')
|
|
1574
|
+
if ((flags & GIT_FS_PATH_REJECT_SLASH) && c == '/')
|
|
1728
1575
|
return false;
|
|
1729
1576
|
|
|
1730
|
-
if (
|
|
1731
|
-
return false;
|
|
1732
|
-
|
|
1733
|
-
if (flags & GIT_PATH_REJECT_NT_CHARS) {
|
|
1577
|
+
if (flags & GIT_FS_PATH_REJECT_NT_CHARS) {
|
|
1734
1578
|
if (c < 32)
|
|
1735
1579
|
return false;
|
|
1736
1580
|
|
|
@@ -1749,211 +1593,166 @@ GIT_INLINE(bool) verify_char(unsigned char c, unsigned int flags)
|
|
|
1749
1593
|
return true;
|
|
1750
1594
|
}
|
|
1751
1595
|
|
|
1752
|
-
/*
|
|
1753
|
-
* Return the length of the common prefix between str and prefix, comparing them
|
|
1754
|
-
* case-insensitively (must be ASCII to match).
|
|
1755
|
-
*/
|
|
1756
|
-
GIT_INLINE(size_t) common_prefix_icase(const char *str, size_t len, const char *prefix)
|
|
1757
|
-
{
|
|
1758
|
-
size_t count = 0;
|
|
1759
|
-
|
|
1760
|
-
while (len >0 && tolower(*str) == tolower(*prefix)) {
|
|
1761
|
-
count++;
|
|
1762
|
-
str++;
|
|
1763
|
-
prefix++;
|
|
1764
|
-
len--;
|
|
1765
|
-
}
|
|
1766
|
-
|
|
1767
|
-
return count;
|
|
1768
|
-
}
|
|
1769
|
-
|
|
1770
1596
|
/*
|
|
1771
1597
|
* We fundamentally don't like some paths when dealing with user-inputted
|
|
1772
|
-
* strings (
|
|
1598
|
+
* strings (to avoid escaping a sandbox): we don't want dot or dot-dot
|
|
1773
1599
|
* anywhere, we want to avoid writing weird paths on Windows that can't
|
|
1774
1600
|
* be handled by tools that use the non-\\?\ APIs, we don't want slashes
|
|
1775
1601
|
* or double slashes at the end of paths that can make them ambiguous.
|
|
1776
1602
|
*
|
|
1777
1603
|
* For checkout, we don't want to recurse into ".git" either.
|
|
1778
1604
|
*/
|
|
1779
|
-
static bool
|
|
1780
|
-
git_repository *repo,
|
|
1605
|
+
static bool validate_component(
|
|
1781
1606
|
const char *component,
|
|
1782
1607
|
size_t len,
|
|
1783
|
-
uint16_t mode,
|
|
1784
1608
|
unsigned int flags)
|
|
1785
1609
|
{
|
|
1786
1610
|
if (len == 0)
|
|
1787
|
-
return
|
|
1611
|
+
return !(flags & GIT_FS_PATH_REJECT_EMPTY_COMPONENT);
|
|
1788
1612
|
|
|
1789
|
-
if ((flags &
|
|
1790
|
-
|
|
1613
|
+
if ((flags & GIT_FS_PATH_REJECT_TRAVERSAL) &&
|
|
1614
|
+
len == 1 && component[0] == '.')
|
|
1791
1615
|
return false;
|
|
1792
1616
|
|
|
1793
|
-
if ((flags &
|
|
1794
|
-
|
|
1617
|
+
if ((flags & GIT_FS_PATH_REJECT_TRAVERSAL) &&
|
|
1618
|
+
len == 2 && component[0] == '.' && component[1] == '.')
|
|
1795
1619
|
return false;
|
|
1796
1620
|
|
|
1797
|
-
if ((flags &
|
|
1621
|
+
if ((flags & GIT_FS_PATH_REJECT_TRAILING_DOT) &&
|
|
1622
|
+
component[len - 1] == '.')
|
|
1798
1623
|
return false;
|
|
1799
1624
|
|
|
1800
|
-
if ((flags &
|
|
1625
|
+
if ((flags & GIT_FS_PATH_REJECT_TRAILING_SPACE) &&
|
|
1626
|
+
component[len - 1] == ' ')
|
|
1801
1627
|
return false;
|
|
1802
1628
|
|
|
1803
|
-
if ((flags &
|
|
1629
|
+
if ((flags & GIT_FS_PATH_REJECT_TRAILING_COLON) &&
|
|
1630
|
+
component[len - 1] == ':')
|
|
1804
1631
|
return false;
|
|
1805
1632
|
|
|
1806
|
-
if (flags &
|
|
1807
|
-
if (!
|
|
1808
|
-
|
|
1809
|
-
|
|
1810
|
-
|
|
1811
|
-
|
|
1812
|
-
|
|
1813
|
-
return false;
|
|
1814
|
-
}
|
|
1815
|
-
|
|
1816
|
-
if (flags & GIT_PATH_REJECT_DOT_GIT_HFS) {
|
|
1817
|
-
if (!verify_dotgit_hfs(component, len))
|
|
1818
|
-
return false;
|
|
1819
|
-
if (S_ISLNK(mode) && git_path_is_gitfile(component, len, GIT_PATH_GITFILE_GITMODULES, GIT_PATH_FS_HFS))
|
|
1820
|
-
return false;
|
|
1821
|
-
}
|
|
1822
|
-
|
|
1823
|
-
if (flags & GIT_PATH_REJECT_DOT_GIT_NTFS) {
|
|
1824
|
-
if (!verify_dotgit_ntfs(repo, component, len))
|
|
1825
|
-
return false;
|
|
1826
|
-
if (S_ISLNK(mode) && git_path_is_gitfile(component, len, GIT_PATH_GITFILE_GITMODULES, GIT_PATH_FS_NTFS))
|
|
1633
|
+
if (flags & GIT_FS_PATH_REJECT_DOS_PATHS) {
|
|
1634
|
+
if (!validate_dospath(component, len, "CON", false) ||
|
|
1635
|
+
!validate_dospath(component, len, "PRN", false) ||
|
|
1636
|
+
!validate_dospath(component, len, "AUX", false) ||
|
|
1637
|
+
!validate_dospath(component, len, "NUL", false) ||
|
|
1638
|
+
!validate_dospath(component, len, "COM", true) ||
|
|
1639
|
+
!validate_dospath(component, len, "LPT", true))
|
|
1827
1640
|
return false;
|
|
1828
1641
|
}
|
|
1829
1642
|
|
|
1830
|
-
/* don't bother rerunning the `.git` test if we ran the HFS or NTFS
|
|
1831
|
-
* specific tests, they would have already rejected `.git`.
|
|
1832
|
-
*/
|
|
1833
|
-
if ((flags & GIT_PATH_REJECT_DOT_GIT_HFS) == 0 &&
|
|
1834
|
-
(flags & GIT_PATH_REJECT_DOT_GIT_NTFS) == 0 &&
|
|
1835
|
-
(flags & GIT_PATH_REJECT_DOT_GIT_LITERAL)) {
|
|
1836
|
-
if (len >= 4 &&
|
|
1837
|
-
component[0] == '.' &&
|
|
1838
|
-
(component[1] == 'g' || component[1] == 'G') &&
|
|
1839
|
-
(component[2] == 'i' || component[2] == 'I') &&
|
|
1840
|
-
(component[3] == 't' || component[3] == 'T')) {
|
|
1841
|
-
if (len == 4)
|
|
1842
|
-
return false;
|
|
1843
|
-
|
|
1844
|
-
if (S_ISLNK(mode) && common_prefix_icase(component, len, ".gitmodules") == len)
|
|
1845
|
-
return false;
|
|
1846
|
-
}
|
|
1847
|
-
}
|
|
1848
|
-
|
|
1849
1643
|
return true;
|
|
1850
1644
|
}
|
|
1851
1645
|
|
|
1852
|
-
|
|
1853
|
-
|
|
1854
|
-
|
|
1646
|
+
#ifdef GIT_WIN32
|
|
1647
|
+
GIT_INLINE(bool) validate_length(
|
|
1648
|
+
const char *path,
|
|
1649
|
+
size_t len,
|
|
1650
|
+
size_t utf8_char_len)
|
|
1855
1651
|
{
|
|
1856
|
-
|
|
1857
|
-
|
|
1858
|
-
|
|
1859
|
-
flags |= GIT_PATH_REJECT_DOT_GIT_LITERAL;
|
|
1652
|
+
GIT_UNUSED(path);
|
|
1653
|
+
GIT_UNUSED(len);
|
|
1860
1654
|
|
|
1861
|
-
|
|
1862
|
-
|
|
1655
|
+
return (utf8_char_len <= MAX_PATH);
|
|
1656
|
+
}
|
|
1863
1657
|
#endif
|
|
1864
1658
|
|
|
1865
|
-
|
|
1866
|
-
|
|
1867
|
-
|
|
1868
|
-
|
|
1659
|
+
bool git_fs_path_str_is_valid_ext(
|
|
1660
|
+
const git_str *path,
|
|
1661
|
+
unsigned int flags,
|
|
1662
|
+
bool (*validate_char_cb)(char ch, void *payload),
|
|
1663
|
+
bool (*validate_component_cb)(const char *component, size_t len, void *payload),
|
|
1664
|
+
bool (*validate_length_cb)(const char *path, size_t len, size_t utf8_char_len),
|
|
1665
|
+
void *payload)
|
|
1666
|
+
{
|
|
1667
|
+
const char *start, *c;
|
|
1668
|
+
size_t len = 0;
|
|
1869
1669
|
|
|
1870
|
-
if (
|
|
1871
|
-
|
|
1872
|
-
if (!error && protectNTFS)
|
|
1873
|
-
flags |= GIT_PATH_REJECT_DOT_GIT_NTFS;
|
|
1670
|
+
if (!flags)
|
|
1671
|
+
return true;
|
|
1874
1672
|
|
|
1875
|
-
|
|
1876
|
-
|
|
1673
|
+
for (start = c = path->ptr; *c && len < path->size; c++, len++) {
|
|
1674
|
+
if (!validate_char(*c, flags))
|
|
1675
|
+
return false;
|
|
1877
1676
|
|
|
1878
|
-
|
|
1879
|
-
|
|
1880
|
-
const char *path,
|
|
1881
|
-
uint16_t mode,
|
|
1882
|
-
unsigned int flags)
|
|
1883
|
-
{
|
|
1884
|
-
const char *start, *c;
|
|
1677
|
+
if (validate_char_cb && !validate_char_cb(*c, payload))
|
|
1678
|
+
return false;
|
|
1885
1679
|
|
|
1886
|
-
|
|
1887
|
-
|
|
1888
|
-
flags = dotgit_flags(repo, flags);
|
|
1680
|
+
if (*c != '/')
|
|
1681
|
+
continue;
|
|
1889
1682
|
|
|
1890
|
-
|
|
1891
|
-
if (!verify_char(*c, flags))
|
|
1683
|
+
if (!validate_component(start, (c - start), flags))
|
|
1892
1684
|
return false;
|
|
1893
1685
|
|
|
1894
|
-
if (
|
|
1895
|
-
|
|
1896
|
-
|
|
1686
|
+
if (validate_component_cb &&
|
|
1687
|
+
!validate_component_cb(start, (c - start), payload))
|
|
1688
|
+
return false;
|
|
1897
1689
|
|
|
1898
|
-
|
|
1899
|
-
}
|
|
1690
|
+
start = c + 1;
|
|
1900
1691
|
}
|
|
1901
1692
|
|
|
1902
|
-
|
|
1903
|
-
|
|
1693
|
+
/*
|
|
1694
|
+
* We want to support paths specified as either `const char *`
|
|
1695
|
+
* or `git_str *`; we pass size as `SIZE_MAX` when we use a
|
|
1696
|
+
* `const char *` to avoid a `strlen`. Ensure that we didn't
|
|
1697
|
+
* have a NUL in the buffer if there was a non-SIZE_MAX length.
|
|
1698
|
+
*/
|
|
1699
|
+
if (path->size != SIZE_MAX && len != path->size)
|
|
1700
|
+
return false;
|
|
1904
1701
|
|
|
1905
|
-
|
|
1906
|
-
|
|
1907
|
-
{
|
|
1908
|
-
int longpaths = 0;
|
|
1702
|
+
if (!validate_component(start, (c - start), flags))
|
|
1703
|
+
return false;
|
|
1909
1704
|
|
|
1910
|
-
if (
|
|
1911
|
-
|
|
1912
|
-
|
|
1705
|
+
if (validate_component_cb &&
|
|
1706
|
+
!validate_component_cb(start, (c - start), payload))
|
|
1707
|
+
return false;
|
|
1913
1708
|
|
|
1914
|
-
|
|
1915
|
-
|
|
1709
|
+
#ifdef GIT_WIN32
|
|
1710
|
+
if ((flags & GIT_FS_PATH_REJECT_LONG_PATHS) != 0) {
|
|
1711
|
+
size_t utf8_len = git_utf8_char_length(path->ptr, len);
|
|
1916
1712
|
|
|
1917
|
-
|
|
1713
|
+
if (!validate_length(path->ptr, len, utf8_len))
|
|
1714
|
+
return false;
|
|
1918
1715
|
|
|
1919
|
-
|
|
1920
|
-
|
|
1921
|
-
|
|
1716
|
+
if (validate_length_cb &&
|
|
1717
|
+
!validate_length_cb(path->ptr, len, utf8_len))
|
|
1718
|
+
return false;
|
|
1719
|
+
}
|
|
1720
|
+
#else
|
|
1721
|
+
GIT_UNUSED(validate_length_cb);
|
|
1722
|
+
#endif
|
|
1922
1723
|
|
|
1923
|
-
return
|
|
1724
|
+
return true;
|
|
1924
1725
|
}
|
|
1925
|
-
#endif
|
|
1926
1726
|
|
|
1927
|
-
int
|
|
1727
|
+
int git_fs_path_validate_str_length_with_suffix(
|
|
1728
|
+
git_str *path,
|
|
1729
|
+
size_t suffix_len)
|
|
1928
1730
|
{
|
|
1929
|
-
|
|
1930
|
-
|
|
1731
|
+
#ifdef GIT_WIN32
|
|
1732
|
+
size_t utf8_len = git_utf8_char_length(path->ptr, path->size);
|
|
1733
|
+
size_t total_len;
|
|
1931
1734
|
|
|
1932
|
-
|
|
1933
|
-
|
|
1735
|
+
if (GIT_ADD_SIZET_OVERFLOW(&total_len, utf8_len, suffix_len) ||
|
|
1736
|
+
total_len > MAX_PATH) {
|
|
1934
1737
|
|
|
1935
|
-
|
|
1936
|
-
|
|
1937
|
-
|
|
1938
|
-
|
|
1939
|
-
|
|
1940
|
-
|
|
1941
|
-
|
|
1738
|
+
git_error_set(GIT_ERROR_FILESYSTEM, "path too long: '%.*s'",
|
|
1739
|
+
(int)path->size, path->ptr);
|
|
1740
|
+
return -1;
|
|
1741
|
+
}
|
|
1742
|
+
#else
|
|
1743
|
+
GIT_UNUSED(path);
|
|
1744
|
+
GIT_UNUSED(suffix_len);
|
|
1745
|
+
#endif
|
|
1942
1746
|
|
|
1943
1747
|
return 0;
|
|
1944
1748
|
}
|
|
1945
1749
|
|
|
1946
|
-
int
|
|
1947
|
-
{
|
|
1948
|
-
return git_path_validate_workdir_with_len(repo, path->ptr, path->size);
|
|
1949
|
-
}
|
|
1950
|
-
|
|
1951
|
-
int git_path_normalize_slashes(git_buf *out, const char *path)
|
|
1750
|
+
int git_fs_path_normalize_slashes(git_str *out, const char *path)
|
|
1952
1751
|
{
|
|
1953
1752
|
int error;
|
|
1954
1753
|
char *p;
|
|
1955
1754
|
|
|
1956
|
-
if ((error =
|
|
1755
|
+
if ((error = git_str_puts(out, path)) < 0)
|
|
1957
1756
|
return error;
|
|
1958
1757
|
|
|
1959
1758
|
for (p = out->ptr; *p; p++) {
|
|
@@ -1964,47 +1763,9 @@ int git_path_normalize_slashes(git_buf *out, const char *path)
|
|
|
1964
1763
|
return 0;
|
|
1965
1764
|
}
|
|
1966
1765
|
|
|
1967
|
-
|
|
1968
|
-
const char *file;
|
|
1969
|
-
const char *hash;
|
|
1970
|
-
size_t filelen;
|
|
1971
|
-
} gitfiles[] = {
|
|
1972
|
-
{ "gitignore", "gi250a", CONST_STRLEN("gitignore") },
|
|
1973
|
-
{ "gitmodules", "gi7eba", CONST_STRLEN("gitmodules") },
|
|
1974
|
-
{ "gitattributes", "gi7d29", CONST_STRLEN("gitattributes") }
|
|
1975
|
-
};
|
|
1976
|
-
|
|
1977
|
-
extern int git_path_is_gitfile(const char *path, size_t pathlen, git_path_gitfile gitfile, git_path_fs fs)
|
|
1978
|
-
{
|
|
1979
|
-
const char *file, *hash;
|
|
1980
|
-
size_t filelen;
|
|
1981
|
-
|
|
1982
|
-
if (!(gitfile >= GIT_PATH_GITFILE_GITIGNORE && gitfile < ARRAY_SIZE(gitfiles))) {
|
|
1983
|
-
git_error_set(GIT_ERROR_OS, "invalid gitfile for path validation");
|
|
1984
|
-
return -1;
|
|
1985
|
-
}
|
|
1986
|
-
|
|
1987
|
-
file = gitfiles[gitfile].file;
|
|
1988
|
-
filelen = gitfiles[gitfile].filelen;
|
|
1989
|
-
hash = gitfiles[gitfile].hash;
|
|
1990
|
-
|
|
1991
|
-
switch (fs) {
|
|
1992
|
-
case GIT_PATH_FS_GENERIC:
|
|
1993
|
-
return !verify_dotgit_ntfs_generic(path, pathlen, file, filelen, hash) ||
|
|
1994
|
-
!verify_dotgit_hfs_generic(path, pathlen, file, filelen);
|
|
1995
|
-
case GIT_PATH_FS_NTFS:
|
|
1996
|
-
return !verify_dotgit_ntfs_generic(path, pathlen, file, filelen, hash);
|
|
1997
|
-
case GIT_PATH_FS_HFS:
|
|
1998
|
-
return !verify_dotgit_hfs_generic(path, pathlen, file, filelen);
|
|
1999
|
-
default:
|
|
2000
|
-
git_error_set(GIT_ERROR_OS, "invalid filesystem for path validation");
|
|
2001
|
-
return -1;
|
|
2002
|
-
}
|
|
2003
|
-
}
|
|
2004
|
-
|
|
2005
|
-
bool git_path_supports_symlinks(const char *dir)
|
|
1766
|
+
bool git_fs_path_supports_symlinks(const char *dir)
|
|
2006
1767
|
{
|
|
2007
|
-
|
|
1768
|
+
git_str path = GIT_STR_INIT;
|
|
2008
1769
|
bool supported = false;
|
|
2009
1770
|
struct stat st;
|
|
2010
1771
|
int fd;
|
|
@@ -2020,13 +1781,13 @@ bool git_path_supports_symlinks(const char *dir)
|
|
|
2020
1781
|
done:
|
|
2021
1782
|
if (path.size)
|
|
2022
1783
|
(void)p_unlink(path.ptr);
|
|
2023
|
-
|
|
1784
|
+
git_str_dispose(&path);
|
|
2024
1785
|
return supported;
|
|
2025
1786
|
}
|
|
2026
1787
|
|
|
2027
|
-
static
|
|
1788
|
+
static git_fs_path_owner_t mock_owner = GIT_FS_PATH_OWNER_NONE;
|
|
2028
1789
|
|
|
2029
|
-
void
|
|
1790
|
+
void git_fs_path__set_owner(git_fs_path_owner_t owner)
|
|
2030
1791
|
{
|
|
2031
1792
|
mock_owner = owner;
|
|
2032
1793
|
}
|
|
@@ -2094,7 +1855,7 @@ static int file_owner_sid(PSID *out, const char *path)
|
|
|
2094
1855
|
PSECURITY_DESCRIPTOR descriptor = NULL;
|
|
2095
1856
|
PSID owner_sid;
|
|
2096
1857
|
DWORD ret;
|
|
2097
|
-
int error =
|
|
1858
|
+
int error = GIT_EINVALID;
|
|
2098
1859
|
|
|
2099
1860
|
if (git_win32_path_from_utf8(path_w32, path) < 0)
|
|
2100
1861
|
return -1;
|
|
@@ -2118,74 +1879,52 @@ static int file_owner_sid(PSID *out, const char *path)
|
|
|
2118
1879
|
return error;
|
|
2119
1880
|
}
|
|
2120
1881
|
|
|
2121
|
-
int
|
|
1882
|
+
int git_fs_path_owner_is(
|
|
1883
|
+
bool *out,
|
|
1884
|
+
const char *path,
|
|
1885
|
+
git_fs_path_owner_t owner_type)
|
|
2122
1886
|
{
|
|
2123
1887
|
PSID owner_sid = NULL, user_sid = NULL;
|
|
2124
|
-
|
|
1888
|
+
BOOL is_admin, admin_owned;
|
|
1889
|
+
int error;
|
|
2125
1890
|
|
|
2126
1891
|
if (mock_owner) {
|
|
2127
|
-
*out = (mock_owner
|
|
1892
|
+
*out = ((mock_owner & owner_type) != 0);
|
|
2128
1893
|
return 0;
|
|
2129
1894
|
}
|
|
2130
1895
|
|
|
2131
|
-
if ((error = file_owner_sid(&owner_sid, path)) < 0
|
|
2132
|
-
(error = current_user_sid(&user_sid)) < 0)
|
|
1896
|
+
if ((error = file_owner_sid(&owner_sid, path)) < 0)
|
|
2133
1897
|
goto done;
|
|
2134
1898
|
|
|
2135
|
-
|
|
2136
|
-
|
|
1899
|
+
if ((owner_type & GIT_FS_PATH_OWNER_CURRENT_USER) != 0) {
|
|
1900
|
+
if ((error = current_user_sid(&user_sid)) < 0)
|
|
1901
|
+
goto done;
|
|
2137
1902
|
|
|
2138
|
-
|
|
2139
|
-
|
|
2140
|
-
|
|
2141
|
-
|
|
2142
|
-
}
|
|
2143
|
-
|
|
2144
|
-
int git_path_owner_is_system(bool *out, const char *path)
|
|
2145
|
-
{
|
|
2146
|
-
PSID owner_sid;
|
|
2147
|
-
|
|
2148
|
-
if (mock_owner) {
|
|
2149
|
-
*out = (mock_owner == GIT_PATH_MOCK_OWNER_SYSTEM);
|
|
2150
|
-
return 0;
|
|
2151
|
-
}
|
|
2152
|
-
|
|
2153
|
-
if (file_owner_sid(&owner_sid, path) < 0)
|
|
2154
|
-
return -1;
|
|
2155
|
-
|
|
2156
|
-
*out = IsWellKnownSid(owner_sid, WinBuiltinAdministratorsSid) ||
|
|
2157
|
-
IsWellKnownSid(owner_sid, WinLocalSystemSid);
|
|
2158
|
-
|
|
2159
|
-
git__free(owner_sid);
|
|
2160
|
-
return 0;
|
|
2161
|
-
}
|
|
2162
|
-
|
|
2163
|
-
int git_path_owner_is_system_or_current_user(bool *out, const char *path)
|
|
2164
|
-
{
|
|
2165
|
-
PSID owner_sid = NULL, user_sid = NULL;
|
|
2166
|
-
int error = -1;
|
|
2167
|
-
|
|
2168
|
-
if (mock_owner) {
|
|
2169
|
-
*out = (mock_owner == GIT_PATH_MOCK_OWNER_SYSTEM ||
|
|
2170
|
-
mock_owner == GIT_PATH_MOCK_OWNER_CURRENT_USER);
|
|
2171
|
-
return 0;
|
|
1903
|
+
if (EqualSid(owner_sid, user_sid)) {
|
|
1904
|
+
*out = true;
|
|
1905
|
+
goto done;
|
|
1906
|
+
}
|
|
2172
1907
|
}
|
|
2173
1908
|
|
|
2174
|
-
|
|
2175
|
-
|
|
1909
|
+
admin_owned =
|
|
1910
|
+
IsWellKnownSid(owner_sid, WinBuiltinAdministratorsSid) ||
|
|
1911
|
+
IsWellKnownSid(owner_sid, WinLocalSystemSid);
|
|
2176
1912
|
|
|
2177
|
-
if (
|
|
2178
|
-
|
|
2179
|
-
*out =
|
|
2180
|
-
error = 0;
|
|
1913
|
+
if (admin_owned &&
|
|
1914
|
+
(owner_type & GIT_FS_PATH_OWNER_ADMINISTRATOR) != 0) {
|
|
1915
|
+
*out = true;
|
|
2181
1916
|
goto done;
|
|
2182
1917
|
}
|
|
2183
1918
|
|
|
2184
|
-
if (
|
|
1919
|
+
if (admin_owned &&
|
|
1920
|
+
(owner_type & GIT_FS_PATH_USER_IS_ADMINISTRATOR) != 0 &&
|
|
1921
|
+
CheckTokenMembership(NULL, owner_sid, &is_admin) &&
|
|
1922
|
+
is_admin) {
|
|
1923
|
+
*out = true;
|
|
2185
1924
|
goto done;
|
|
1925
|
+
}
|
|
2186
1926
|
|
|
2187
|
-
*out =
|
|
2188
|
-
error = 0;
|
|
1927
|
+
*out = false;
|
|
2189
1928
|
|
|
2190
1929
|
done:
|
|
2191
1930
|
git__free(owner_sid);
|
|
@@ -2195,12 +1934,36 @@ done:
|
|
|
2195
1934
|
|
|
2196
1935
|
#else
|
|
2197
1936
|
|
|
2198
|
-
static int
|
|
1937
|
+
static int sudo_uid_lookup(uid_t *out)
|
|
1938
|
+
{
|
|
1939
|
+
git_str uid_str = GIT_STR_INIT;
|
|
1940
|
+
int64_t uid;
|
|
1941
|
+
int error;
|
|
1942
|
+
|
|
1943
|
+
if ((error = git__getenv(&uid_str, "SUDO_UID")) == 0 &&
|
|
1944
|
+
(error = git__strntol64(&uid, uid_str.ptr, uid_str.size, NULL, 10)) == 0 &&
|
|
1945
|
+
uid == (int64_t)((uid_t)uid)) {
|
|
1946
|
+
*out = (uid_t)uid;
|
|
1947
|
+
}
|
|
1948
|
+
|
|
1949
|
+
git_str_dispose(&uid_str);
|
|
1950
|
+
return error;
|
|
1951
|
+
}
|
|
1952
|
+
|
|
1953
|
+
int git_fs_path_owner_is(
|
|
1954
|
+
bool *out,
|
|
1955
|
+
const char *path,
|
|
1956
|
+
git_fs_path_owner_t owner_type)
|
|
2199
1957
|
{
|
|
2200
1958
|
struct stat st;
|
|
2201
|
-
|
|
1959
|
+
uid_t euid, sudo_uid;
|
|
2202
1960
|
|
|
2203
|
-
|
|
1961
|
+
if (mock_owner) {
|
|
1962
|
+
*out = ((mock_owner & owner_type) != 0);
|
|
1963
|
+
return 0;
|
|
1964
|
+
}
|
|
1965
|
+
|
|
1966
|
+
euid = geteuid();
|
|
2204
1967
|
|
|
2205
1968
|
if (p_lstat(path, &st) != 0) {
|
|
2206
1969
|
if (errno == ENOENT)
|
|
@@ -2210,51 +1973,94 @@ static int path_owner_is(bool *out, const char *path, uid_t *uids, size_t uids_l
|
|
|
2210
1973
|
return -1;
|
|
2211
1974
|
}
|
|
2212
1975
|
|
|
2213
|
-
|
|
2214
|
-
|
|
2215
|
-
|
|
2216
|
-
|
|
2217
|
-
}
|
|
1976
|
+
if ((owner_type & GIT_FS_PATH_OWNER_CURRENT_USER) != 0 &&
|
|
1977
|
+
st.st_uid == euid) {
|
|
1978
|
+
*out = true;
|
|
1979
|
+
return 0;
|
|
2218
1980
|
}
|
|
2219
1981
|
|
|
2220
|
-
|
|
2221
|
-
|
|
2222
|
-
|
|
2223
|
-
|
|
2224
|
-
|
|
2225
|
-
uid_t userid = geteuid();
|
|
1982
|
+
if ((owner_type & GIT_FS_PATH_OWNER_ADMINISTRATOR) != 0 &&
|
|
1983
|
+
st.st_uid == 0) {
|
|
1984
|
+
*out = true;
|
|
1985
|
+
return 0;
|
|
1986
|
+
}
|
|
2226
1987
|
|
|
2227
|
-
if (
|
|
2228
|
-
|
|
1988
|
+
if ((owner_type & GIT_FS_PATH_OWNER_RUNNING_SUDO) != 0 &&
|
|
1989
|
+
euid == 0 &&
|
|
1990
|
+
sudo_uid_lookup(&sudo_uid) == 0 &&
|
|
1991
|
+
st.st_uid == sudo_uid) {
|
|
1992
|
+
*out = true;
|
|
2229
1993
|
return 0;
|
|
2230
1994
|
}
|
|
2231
1995
|
|
|
2232
|
-
|
|
1996
|
+
*out = false;
|
|
1997
|
+
return 0;
|
|
2233
1998
|
}
|
|
2234
1999
|
|
|
2235
|
-
|
|
2236
|
-
{
|
|
2237
|
-
uid_t userid = 0;
|
|
2000
|
+
#endif
|
|
2238
2001
|
|
|
2239
|
-
|
|
2240
|
-
|
|
2241
|
-
|
|
2242
|
-
|
|
2002
|
+
int git_fs_path_owner_is_current_user(bool *out, const char *path)
|
|
2003
|
+
{
|
|
2004
|
+
return git_fs_path_owner_is(out, path, GIT_FS_PATH_OWNER_CURRENT_USER);
|
|
2005
|
+
}
|
|
2243
2006
|
|
|
2244
|
-
|
|
2007
|
+
int git_fs_path_owner_is_system(bool *out, const char *path)
|
|
2008
|
+
{
|
|
2009
|
+
return git_fs_path_owner_is(out, path, GIT_FS_PATH_OWNER_ADMINISTRATOR);
|
|
2245
2010
|
}
|
|
2246
2011
|
|
|
2247
|
-
int
|
|
2012
|
+
int git_fs_path_find_executable(git_str *fullpath, const char *executable)
|
|
2248
2013
|
{
|
|
2249
|
-
|
|
2014
|
+
#ifdef GIT_WIN32
|
|
2015
|
+
git_win32_path fullpath_w, executable_w;
|
|
2016
|
+
int error;
|
|
2250
2017
|
|
|
2251
|
-
if (
|
|
2252
|
-
|
|
2253
|
-
|
|
2254
|
-
|
|
2018
|
+
if (git__utf8_to_16(executable_w, GIT_WIN_PATH_MAX, executable) < 0)
|
|
2019
|
+
return -1;
|
|
2020
|
+
|
|
2021
|
+
error = git_win32_path_find_executable(fullpath_w, executable_w);
|
|
2022
|
+
|
|
2023
|
+
if (error == 0)
|
|
2024
|
+
error = git_str_put_w(fullpath, fullpath_w, wcslen(fullpath_w));
|
|
2025
|
+
|
|
2026
|
+
return error;
|
|
2027
|
+
#else
|
|
2028
|
+
git_str path = GIT_STR_INIT;
|
|
2029
|
+
const char *current_dir, *term;
|
|
2030
|
+
bool found = false;
|
|
2031
|
+
|
|
2032
|
+
if (git__getenv(&path, "PATH") < 0)
|
|
2033
|
+
return -1;
|
|
2034
|
+
|
|
2035
|
+
current_dir = path.ptr;
|
|
2036
|
+
|
|
2037
|
+
while (*current_dir) {
|
|
2038
|
+
if (! (term = strchr(current_dir, GIT_PATH_LIST_SEPARATOR)))
|
|
2039
|
+
term = strchr(current_dir, '\0');
|
|
2040
|
+
|
|
2041
|
+
git_str_clear(fullpath);
|
|
2042
|
+
if (git_str_put(fullpath, current_dir, (term - current_dir)) < 0 ||
|
|
2043
|
+
git_str_putc(fullpath, '/') < 0 ||
|
|
2044
|
+
git_str_puts(fullpath, executable) < 0)
|
|
2045
|
+
return -1;
|
|
2046
|
+
|
|
2047
|
+
if (git_fs_path_isfile(fullpath->ptr)) {
|
|
2048
|
+
found = true;
|
|
2049
|
+
break;
|
|
2050
|
+
}
|
|
2051
|
+
|
|
2052
|
+
current_dir = term;
|
|
2053
|
+
|
|
2054
|
+
while (*current_dir == GIT_PATH_LIST_SEPARATOR)
|
|
2055
|
+
current_dir++;
|
|
2255
2056
|
}
|
|
2256
2057
|
|
|
2257
|
-
|
|
2258
|
-
|
|
2058
|
+
git_str_dispose(&path);
|
|
2059
|
+
|
|
2060
|
+
if (found)
|
|
2061
|
+
return 0;
|
|
2259
2062
|
|
|
2063
|
+
git_str_clear(fullpath);
|
|
2064
|
+
return GIT_ENOTFOUND;
|
|
2260
2065
|
#endif
|
|
2066
|
+
}
|