aboutsummaryrefslogtreecommitdiffstats
path: root/org.eclipse.jgit
Commit message (Collapse)AuthorAgeFilesLines
...
* Fix push option initalization on HTTPStefan Beller2016-08-261-1/+3
| | | | | | | | | | | Initialize pushOptions when we decide to use them, instead of when we advertise them. In the case of HTTP the advertisement is in a different network request, hence in a different instance of the BaseReceivePack. Change-Id: I094c60942e04de82cb6d8433c9cd43a46ffae332 Signed-off-by: Stefan Beller <sbeller@google.com>
* Merge "DfsReader: check object type during open"Shawn Pearce2016-08-252-4/+17
|\
| * DfsReader: check object type during openShawn Pearce2016-08-252-4/+17
| | | | | | | | | | | | | | | | | | Do not open an OBJ_TREE if the caller is expecting an OBJ_BLOB or OBJ_COMMIT; instead throw IncorrectObjectTypeException. This better matches behavior of WindowCursor, the ObjectReader implementation of the local file based object store. Change-Id: I3fb0e77f54895b123679a405e1b6ba5b95752ff0
* | Clarify the semantics of DfsRefDatabase#compareAndPutMasaya Suzuki2016-08-252-26/+17
|/ | | | | | | | | | | | | | | | | | | | | | | | | | | DfsRefDatabase#compareAndPut had a vague semantics for reference matching. Because of this, an operation to make a symbolic reference had been broken for some DFS implementations even if they followed the contract of compareAndPut. The clarified semantics requires the implementations to satisfy the followings: * Matching references should be both symbolic references or both object ID references. * If both are symbolic references, both should have the same target name. * If both are object ID references, both should have the same object ID. This semantics is defined based on https://git.eclipse.org/r/#/c/77416/. Before this commit, DfsRefDatabase couldn't see the target of symbolic references. InMemoryRepository is changed to comply with the new semantics. This semantics change can affect the existing DFS implementations that only checks object IDs. This commit adds two tests that the previous InMemoryRepository couldn't pass. Change-Id: I6c6b5d3cc8241a81f4a37782381c88e8a59fdf15 Signed-off-by: Masaya Suzuki <masayasuzuki@google.com>
* Do not fake a SymbolicRef as an ObjectIdRefMasaya Suzuki2016-08-254-11/+12
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When doing a detaching operation, JGit fakes a SymbolicRef as an ObjectIdRef. This is because RefUpdate#updateImpl dereferences the SymbolicRef when updating it. For example, assume that HEAD is pointing to refs/heads/master. If I try to make a detached HEAD pointing to a commit c0ffee, RefUpdate dereferences HEAD as refs/heads/master first and changes refs/heads/master to c0ffee. The detach argument of RefDatabase#newUpdate avoids this dereference by faking HEAD as ObjectIdRef. This faking is problematic for the linking operation of DfsRefDatabase. It does a compare-and-swap operation on every reference change because of its distributed systems nature. If a SymbolicRef is faked as an ObjectRef, it thinks that there is a racing change in the reference and rejects the update. Because of this, DFS based repositories cannot change the link target of symbolic refs. This has not been a problem for file-based repositories because they have a file-lock based semantics instead of the CAS based one. The reference implementation, InMemoryRepository, is not affected because it only compares ObjectIds. When [1] introduced this faking code, there was no way for RefUpdate to distinguish the detaching operation. When [2] fixed the detaching operation, it introduced a detachingSymbolicRef flag. This commit uses this flag to control whether it needs to dereference the symbolic refs by calling Ref#getLeaf. The same flag is used in the reflog update operation. This commit does not affect any operation that succeeds currently. In some DFS repository implementations, this fixes a ref linking operation, which is currently failing. [1]: https://eclipse.googlesource.com/jgit/jgit/+/01b5392cdbc12ce2e21fd1d1afbd61fdf97e1c38 [2]: https://eclipse.googlesource.com/jgit/jgit/+/3a86868c0883d2a564db88bf9ae4a5fe235bb63f Change-Id: I118f85f0414dbfad02250944e28d74dddd59469b Signed-off-by: Masaya Suzuki <masayasuzuki@google.com>
* Packet logging for JGitDan Wang2016-08-242-5/+31
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Imitate the packet tracing feature from C Git v1.7.5-rc0~58^2~1 (add packet tracing debug code, 2011-02-24). Unlike C Git, use the log4j log level setting instead of the GIT_TRACE_PACKET environment variable to enable tracing. Tested as follows: 1. Enable tracing by adding the lines log4j.logger.org.eclipse.jgit.transport=DEBUG, stderr log4j.additivity.org.eclipse.jgit.transport=false to org.eclipse.jgit.pgm/resources/log4j.properties. 2. mvn package 3. org.eclipse.jgit.pgm/target/jgit \ ls-remote git://git.kernel.org/pub/scm/git/git 2>&1 |less Then the output provides a trace of packets sent and received over the wire: 2016-08-24 16:36:42 DEBUG PacketLineOut:145 - git> git-upload-pack /pub/scm/git/git^@host=git.kernel.org^@ 2016-08-24 16:36:42 DEBUG PacketLineIn:165 - git< 2632c897f74b1cc9b5533f467da459b9ec725538 HEAD^@multi_ack thin-pack side-band side-band-64k ofs-delta shallow no-progress include-tag multi_ack_detailed symref=HEAD:refs/heads/master agent=git/2.8.4 2016-08-24 16:36:42 DEBUG PacketLineIn:165 - git< e0c1ceafc5bece92d35773a75fff59497e1d9bd5 refs/heads/maint Change-Id: I5028c064f3ac090510386057cb4e6d30d4eae232 Signed-off-by: Dan Wang <dwwang@google.com>
* Use FS#lastModified instead of File#lastModifiedMasaya Suzuki2016-08-244-8/+22
| | | | | | | | | | | | | | | This fixes the tests failed in JDK8. FS uses java.nio API to get file attributes. The timestamps obtained from that API are more precise than the ones from java.io.File#lastModified() since Java8. This difference accidentally makes JGit detect newly added files as smudged. Use the precised timestamp to avoid this false positive. Bug: 500058 Change-Id: I9e587583c85cb6efa7562ad6c5f26577869a2e7c Signed-off-by: Masaya Suzuki <masayasuzuki@google.com> Signed-off-by: Andrey Loskutov <loskutov@gmx.de>
* Don't check lastModified, length on folders for submodulesChristian Halstrick2016-08-241-3/+13
| | | | | | | | The metadata comparison of submodules is not reliable because of the last modified timestamp and directory length. Bug: 498759 Change-Id: If5db69ef3868e475ac477d3e8a7750b268799b0c
* Add HTTP status code to ServiceMayNotContinueExceptionMasaya Suzuki2016-08-234-2/+51
| | | | | | | | The exception can be thrown in a various reason, and sometimes 403 Forbidden is not appropriate. Make the HTTP status code customizable. Change-Id: If2ef6f454f7479158a4e28a12909837db483521c Signed-off-by: Masaya Suzuki <masayasuzuki@google.com>
* Merge "Ignore IOException thrown from close"Shawn Pearce2016-08-191-1/+10
|\
| * Ignore IOException thrown from closeMasaya Suzuki2016-08-191-1/+10
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | AddCommandTest is flaky because IOException is thrown sometimes. Caused by: java.io.IOException: Stream closed at java.lang.ProcessBuilder$NullOutputStream.write(ProcessBuilder.java:433) at java.io.OutputStream.write(OutputStream.java:116) at java.io.BufferedOutputStream.flushBuffer(BufferedOutputStream.java:82) at java.io.BufferedOutputStream.flush(BufferedOutputStream.java:140) at java.io.FilterOutputStream.close(FilterOutputStream.java:158) at org.eclipse.jgit.util.FS.runProcess(FS.java:993) at org.eclipse.jgit.util.FS.execute(FS.java:1102) at org.eclipse.jgit.treewalk.WorkingTreeIterator.filterClean(WorkingTreeIterator.java:470) ... 22 more OpenJDK replaces the underlying OutputStream with NullOutputStream when the process exits. This throws IOException for all write operation. When it exits before JGit writes the input to the pipe buffer, the input stays in BufferedOutputStream. The close method tries to write it again, and IOException is thrown. Since we ignore IOException in StreamGobbler, we also ignore it when we close the stream. Fixes Bug 499633. Change-Id: I30c7ac78e05b00bd0152f697848f4d17d53efd17 Signed-off-by: Masaya Suzuki <draftcode@gmail.com>
* | DfsObjDatabase: clear PackList dirty bit if no new packsShawn Pearce2016-08-191-1/+14
|/ | | | | | | | | | | If a reference was updated more recently than a pack was written (typical) the PackList was perpetually dirty until the next GC was completed for the repository. Detect this condition by observing no changes to the PackList membership and resetting the dirty bit. Change-Id: Ie2133aca1f8083307c73b6a26358175864f100ef
* Enhance ResetCommand to allow disabling reflog updateMatthias Sohn2016-08-171-2/+28
| | | | | | | This will be used by EGit for implementing commit amend in the staging view (see Idcd1efeeee8b3065bae36e285bfc0af24ab1e88f). Change-Id: Ice9ebbb1c0c3314c679f4db40cdd3664f61c27c3 Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>
* Merge "BaseReceivePack: null and IllegalStateException cases for getPushOptions"Jonathan Nieder2016-08-151-3/+19
|\
| * BaseReceivePack: null and IllegalStateException cases for getPushOptionsDan Wang2016-08-101-3/+19
| | | | | | | | | | Change-Id: I5c6790719991931d615d821c900bfd90a20e540b Signed-off-by: Dan Wang <dwwang@google.com>
* | RepoCommand: Avoid group lists shadowing groups stringsJonathan Nieder2016-08-082-10/+10
| | | | | | | | | | | | Reported-by: David Pursehouse <david.pursehouse@gmail.com> Change-Id: I9e9b021d335bda4d58b6bcc30f59b81ac5b37724 Signed-off-by: Jonathan Nieder <jrn@google.com>
* | PackWriter: Fix Javadoc tag for thrown exception in preparePackDavid Pursehouse2016-08-091-1/+1
| | | | | | | | | | | | | | Use @throws instead of @param Change-Id: Ic9419d254c617e60a9b10e49205b11069442eb27 Signed-off-by: David Pursehouse <david.pursehouse@gmail.com>
* | Merge "Document new PackWriter#preparePack variant's parameters and exceptions"Jonathan Nieder2016-08-081-0/+20
|\ \
| * | Document new PackWriter#preparePack variant's parameters and exceptionsJonathan Nieder2016-08-081-0/+20
| | | | | | | | | | | | Change-Id: Id4fa272c611a855bf4ef1bf5399f3e4305664103
* | | Add missing @since tags for new APIMatthias Sohn2016-08-091-0/+3
| | | | | | | | | | | | Change-Id: I8db29a0313fbc476152cef47f2eaa76954f1e280 Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>
* | | Merge "Require-Bundle com.jcraft.jsch replaced by Import-Package statement"Matthias Sohn2016-08-081-1/+1
|\ \ \ | |/ / |/| |
| * | Require-Bundle com.jcraft.jsch replaced by Import-Package statementJens Offenbach2016-08-091-1/+1
| | | | | | | | | | | | | | | | | | Bug: 359288 Change-Id: Ifbbf953f5389c6bd3ba960b598c0e92656b522e3 Signed-off-by: Jens Offenbach <wolle5050@gmx.de> Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>
* | | Merge changes Ib0d8c294,Idfb83482Jonathan Nieder2016-08-082-6/+30
|\ \ \ | |/ / |/| | | | | | | | | | | | | | | | | * changes: Shallow fetch: Pass along "shallow"s in unparsed-wants case, too Shallow fetch: Pass a DepthWalk to PackWriter Change-Id: I7d1c3b4d0b7ebc254b53404d1618522b0174ac23
| * | Shallow fetch: Pass along "shallow"s in unparsed-wants case, tooJonathan Nieder2016-08-082-3/+24
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Since 84d2738ff21c (Don't skip want validation when the client sends no haves, 2013-06-21), this branch is not taken. Process the "shallow"s anyway as a defensive measure in case the code path gets revived. Change-Id: Idfb834825d77f51e17191c1635c9d78c78738cfd Signed-off-by: Jonathan Nieder <jrn@google.com>
| * | Shallow fetch: Pass a DepthWalk to PackWriterJonathan Nieder2016-08-081-3/+6
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | d385a7a5e5ca (Shallow fetch: Respect "shallow" lines, 2016-08-03) forgot that UploadPack wasn't passing a DepthWalk to PackWriter in the first place. As a result, shallow clones fail: java.lang.IllegalArgumentException: Shallow packs require a DepthWalk at org.eclipse.jgit.internal.storage.pack.PackWriter.preparePack(PackWriter.java:756) at org.eclipse.jgit.transport.UploadPack.sendPack(UploadPack.java:1497) at org.eclipse.jgit.transport.UploadPack.sendPack(UploadPack.java:1381) at org.eclipse.jgit.transport.UploadPack.service(UploadPack.java:774) at org.eclipse.jgit.transport.UploadPack.upload(UploadPack.java:667) at org.eclipse.jgit.http.server.UploadPackServlet.doPost(UploadPackServlet.java:191) Change-Id: Ib0d8c2946eebfea910a2b767fb92e23da15d4749
* | | Merge "Skip cleaning inner repositories by default in CleanCommand"Christian Halstrick2016-08-071-11/+73
|\ \ \
| * | | Skip cleaning inner repositories by default in CleanCommandMatthaus Owens2016-08-041-11/+73
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Previously jgit would attempt to clean git repositories that had not been committed by calling a non-recursive delete on them, which would fail as they are directories. This commit addresses that issue in the following ways. Repositories are skipped in a default clean, similarly to cgit and only cleaned when the force flag is applied. When the force flag is applied repositories are deleted using a recursive delete call. The force flag and setForce method are added here to CleanCommand to support this change. Bug: 498367 Change-Id: Ib6cfff65a033d0d0f76395060bf76719e13fc467 Signed-off-by: Matthaus Owens <matthaus@puppetlabs.com>
* | | | Shallow fetch/clone: Make --depth mean the total history depthTerry Parker2016-08-054-6/+18
| |/ / |/| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | cgit changed the --depth parameter to mean the total depth of history rather than the depth of ancestors to be returned [1]. JGit still uses the latter meaning, so update it to match cgit. depth=0 still means a non-shallow clone. depth=1 now means only the wants rather than the wants and their direct parents. This is accomplished by changing the semantic meaning of "depth" in UploadPack and PackWriter to mean the total depth of history desired, while keeping "depth" in DepthWalk.{RevWalk,ObjectWalk} to mean the depth of traversal. Thus UploadPack and PackWriter always initialize their DepthWalks with "depth-1". [1] upload-pack: fix off-by-one depth calculation in shallow clone https://code.googlesource.com/git/+/682c7d2f1a2d1a5443777237450505738af2ff1a Change-Id: I87ed3c0f56c37e3491e367a41f5e555c4207ff44 Signed-off-by: Terry Parker <tparker@google.com>
* | | Shallow fetch: Respect "shallow" linesTerry Parker2016-08-054-2/+13
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When fetching from a shallow clone, the client sends "have" lines to tell the server about objects it already has and "shallow" lines to tell where its local history terminates. In some circumstances, the server fails to honor the shallow lines and fails to return objects that the client needs. UploadPack passes the "have" lines to PackWriter so PackWriter can omit them from the generated pack. UploadPack processes "shallow" lines by calling RevWalk.assumeShallow() with the set of shallow commits. RevWalk creates and caches RevCommits for these shallow commits, clearing out their parents. That way, walks correctly terminate at the shallow commits instead of assuming the client has history going back behind them. UploadPack converts its RevWalk to an ObjectWalk, maintaining the cached RevCommits, and passes it to PackWriter. Unfortunately, to support shallow fetches the PackWriter does the following: if (shallowPack && !(walk instanceof DepthWalk.ObjectWalk)) walk = new DepthWalk.ObjectWalk(reader, depth); That is, when the client sends a "deepen" line (fetch --depth=<n>) and the caller has not passed in a DepthWalk.ObjectWalk, PackWriter throws away the RevWalk that was passed in and makes a new one. The cleared parent lists prepared by RevWalk.assumeShallow() are lost. Fortunately UploadPack intends to pass in a DepthWalk.ObjectWalk. It tries to create it by calling toObjectWalkWithSameObjects() on a DepthWalk.RevWalk. But it doesn't work: because DepthWalk.RevWalk does not override the standard RevWalk#toObjectWalkWithSameObjects implementation, the result is a plain ObjectWalk instead of an instance of DepthWalk.ObjectWalk. The result is that the "shallow" information is thrown away and objects reachable from the shallow commits can be omitted from the pack sent when fetching with --depth from a shallow clone. Multiple factors collude to limit the circumstances under which this bug can be observed: 1. Commits with depth != 0 don't enter DepthGenerator's pending queue. That means a "have" cannot have any effect on DepthGenerator unless it is also a "want". 2. DepthGenerator#next() doesn't call carryFlagsImpl(), so the uninteresting flag is not propagated to ancestors there even if a "have" is also a "want". 3. JGit treats a depth of 1 as "1 past the wants". Because of (2), the only place the UNINTERESTING flag can leak to a shallow commit's parents is in the carryFlags() call from markUninteresting(). carryFlags() only traverses commits that have already been parsed: commits yet to be parsed are supposed to inherit correct flags from their parent in PendingGenerator#next (which doesn't happen here --- that is (2)). So the list of commits that have already been parsed becomes relevant. When we hit the markUninteresting() call, all "want"s, "have"s, and commits to be unshallowed have been parsed. carryFlags() only affects the parsed commits. If the "want" is a direct parent of a "have", then it carryFlags() marks it as uninteresting. If the "have" was also a "shallow", then its parent pointer should have been null and the "want" shouldn't have been marked, so we see the bug. If the "want" is a more distant ancestor then (2) keeps the uninteresting state from propagating to the "want" and we don't see the bug. If the "shallow" is not also a "have" then the shallow commit isn't parsed so (2) keeps the uninteresting state from propagating to the "want so we don't see the bug. Here is a reproduction case (time flowing left to right, arrows pointing to parents). "C" must be a commit that the client reports as a "have" during negotiation. That can only happen if the server reports it as an existing branch or tag in the first round of negotiation: A <-- B <-- C <-- D First do git clone --depth 1 <repo> which yields D as a "have" and C as a "shallow" commit. Then try git fetch --depth 1 <repo> B:refs/heads/B Negotiation sets up: have D, shallow C, have C, want B. But due to this bug B is marked as uninteresting and is not sent. Change-Id: I6e14b57b2f85e52d28cdcf356df647870f475440 Signed-off-by: Terry Parker <tparker@google.com>
* | | Merge changes from topic 'shallowClone'Jonathan Nieder2016-08-042-3/+19
|\ \ \ | | | | | | | | | | | | | | | | | | | | * changes: RevWalk: Make fields available to DepthWalk Shallow fetch: avoid sending unneeded blobs
| * | | RevWalk: Make fields available to DepthWalkTerry Parker2016-08-041-1/+1
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | DepthWalk needs to override toObjectWalkWithSameObjects() and thus needs to be able to directly set the objects and freeFlags fields, so make them package private. Change-Id: I24561b82c54ba3d6522582ca25105b204d777074 Signed-off-by: Terry Parker <tparker@google.com>
| * | | Shallow fetch: avoid sending unneeded blobsTerry Parker2016-08-041-2/+18
| |/ / | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | When doing an incremental fetch from JGit, "have" commits are marked as "uninteresting". In a non-shallow fetch, when the RevWalk hits an "uninteresting" commit it marks the commit's corresponding tree as uninteresting. That has the effect of dropping those trees and all the trees and blobs they reference out of the thin pack returned to the client. However, shallow fetches use a DepthWalk to limit the RevWalk, which nearly always causes the RevWalk to terminate before encountering the "have" commits. As a result the pack created for the incremental fetch never encounters "uninteresting" tree objects and thus includes duplicate objects that it knows the client already has. Change-Id: I7b1f7c3b0d83e04d34cd2fa676f1ad4fec904c05 Signed-off-by: Terry Parker <tparker@google.com>
* / / DiffFormatter: Support setting a reader without a repoDave Borowitz2016-08-033-25/+42
|/ / | | | | | | Change-Id: I575cdb9c0a9a341b79ef5e3c7a35e68cde142540
* | Merge "RefSpec: Make WildcardMode public"Jonathan Nieder2016-07-281-2/+20
|\ \
| * | RefSpec: Make WildcardMode publicStefan Beller2016-07-281-2/+20
| | | | | | | | | | | | | | | | | | | | | | | | We have to be able to access the enum from outside the package as part of the API. Change-Id: I4bdc6bd53a14237c5f4fb9397ae850f9a24c4cfb Signed-off-by: Stefan Beller <sbeller@google.com>
* | | MergeFormatter: Suppress warning about unchecked conversionDavid Pursehouse2016-07-261-0/+1
|/ / | | | | | | | | | | | | | | | | | | | | | | | | | | The warning can be fixed by adding a type to the argument, but doing so breaks the API and previous attempts to fix it in that way [1, 2] were reverted [3, 4]. [1] https://git.eclipse.org/r/#/c/45709/ [2] https://git.eclipse.org/r/#/c/66602/ [3] https://git.eclipse.org/r/#/c/49400/ [4] https://git.eclipse.org/r/#/c/66659/ Change-Id: I01dd52e09da24f70d408ffa96e21c129a79041ea Signed-off-by: David Pursehouse <david.pursehouse@gmail.com>
* | Repository: Log negative useCnt message together with stack traceDavid Pursehouse2016-07-261-2/+3
| | | | | | | | | | | | | | | | | | | | | | | | | | The message "close() called when useCnt is already zero" is logged with level warning, and then if debug logging is enabled, the stack trace is logged separately with level debug. Log the message and the stack trace in the same call, so that they always appear together in the output rather than potentially interleaved with other log statements. Change-Id: I1b5c1557ddc2d19f3f5b29baec96e62bc467d88a Signed-off-by: David Pursehouse <david.pursehouse@gmail.com>
* | Ignore 'The value of exception parameter is not used' warningDavid Pursehouse2016-07-261-0/+1
| | | | | | | | | | Change-Id: I50407e4a33e35b718ca40503fdd436f1f9f70fba Signed-off-by: David Pursehouse <david.pursehouse@gmail.com>
* | Merge branch 'stable-4.4'David Pursehouse2016-07-261-4/+15
|\ \ | | | | | | | | | | | | | | | | | | | | | | | | * stable-4.4: JGit v4.4.1.201607150455-r RefDirectory: remove ref lock file for following ref dir removal Change-Id: Ifc8a782efd7f2f991e70ad2a3691a8dba66c7554 Signed-off-by: David Pursehouse <david.pursehouse@gmail.com>
| * | JGit v4.4.1.201607150455-rv4.4.1.201607150455-rMatthias Sohn2016-07-153-4/+4
| | | | | | | | | | | | | | | Change-Id: I61dbc29a962c8185fb356fe1ca30a1e673166d47 Signed-off-by: Matthias Sohn <matthias.sohn@sap.com>
| * | Merge "RefDirectory: remove ref lock file for following ref dir removal" ↵Christian Halstrick2016-07-151-4/+15
| |\ \ | | | | | | | | | | | | into stable-4.4
| | * | RefDirectory: remove ref lock file for following ref dir removalMarco Miller2016-06-101-4/+15
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Before this fix, ref directory removal did not work. That was because the ref lock file was still in the leaf directory at deletion time. Hence no deep ref directories were ever deleted, which negatively impacted performance under large directory structure circumstances. This fix removes the ref lock file before attempting to delete the ref directory (which includes it). The other deep parent directories are therefore now successfully deleted in turn, since leaf's content (lock file) gets removed first. So, given a structure such as refs/any/directory[/**], this fix now deletes all empty directories up to -and including- 'directory'. The 'any' directory (e.g.) does not get deleted even if empty, as before. The ref lock file is still also removed in the calling block's finally clause, just in case, as before. Such double-unlock brought by this fix is harmless (a no-op). A new (private) RefDirectory#delete method is introduced to support this #pack-specific case; other RefDirectory#delete callers remain untouched. Change-Id: I47ba1eeb9bcf0cb93d2ed105d84fea2dac756a5a Signed-off-by: Marco Miller <marco.miller@ericsson.com>
* | | | RefSpecs: allow construction of weird wildcarded RefSpecsStefan Beller2016-07-253-9/+86
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Gerrit's superproject subscription feature uses RefSpecs to formalize the ACLs of when the superproject subscription feature is allowed. As this is a slightly different use case than describing a local/remote pair of refs, we need to be more permissive. Specifically we want to allow: refs/heads/* refs/heads/*:refs/heads/master refs/heads/master:refs/heads/* Introduce a new constructor, that allows constructing these RefSpecs. Change-Id: I46c0bea9d876e61eb2c8d50f404b905792bc72b3 Signed-off-by: Stefan Beller <sbeller@google.com>
* | | | RefSpec: reject refs ending in '/'Stefan Beller2016-07-251-0/+2
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | We had a case in Gerrits superproject subscriptions where 'refs/heads/' was configured with the intention to mean 'refs/heads/*'. The first expression lacks the '*', which is why it is not considered a wildcard but it was considered valid and so was not found early to be a typo. Refs are not allowed to end with '/' anyway, so add a check for that. Change-Id: I3ffdd9002146382acafb4fbc310a64af4cc1b7a9 Signed-off-by: Stefan Beller <sbeller@google.com>
* | | | Merge "Push implementation of option strings"Terry Parker2016-07-2210-6/+244
|\ \ \ \ | | |_|/ | |/| |
| * | | Push implementation of option stringsDan Wang2016-07-2210-6/+244
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Example usage: $ ./jgit push \ --push-option "Reviewer=j.doe@example.org" \ --push-option "<arbitrary string>" \ origin HEAD:refs/for/master Stefan Beller has also made an equivalent change to CGit: http://thread.gmane.org/gmane.comp.version-control.git/299872 Change-Id: I6797e50681054dce3bd179e80b731aef5e200d77 Signed-off-by: Dan Wang <dwwang@google.com>
* | | | DfsObjDatabase: Add lazy last modified method to PackListDave Borowitz2016-07-191-0/+14
| | | | | | | | | | | | | | | | Change-Id: Id045f162fa584ea14da29a9df58a42c53a78dc15
* | | | Merge changes I159e9154,I06c722b2Dave Borowitz2016-07-193-43/+188
|\ \ \ \ | |/ / / |/| | | | | | | | | | | | | | | * changes: DfsObjectDatabase: Expose PackList and move markDirty there Invalidate DfsObjDatabase pack list when refs are updated
| * | | DfsObjectDatabase: Expose PackList and move markDirty thereDave Borowitz2016-07-182-20/+37
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | What's invalidated when an object database is "dirty" is not the whole database, but rather a specific list of packs. If there is a race between getting the pack list and setting the volatile dirty flag where the packs are rescanned, we don't need to mark the new pack list as dirty. This is a fine point that only really applies if the decision of whether or not to mark dirty actually requires introspecting the pack list (say, its timestamps). The general operation of "take whatever is the current pack list and mark it dirty" may still be inherently racy, but the cost is not so high. Change-Id: I159e9154bd8b2d348b4e383627a503e85462dcc6
| * | | Invalidate DfsObjDatabase pack list when refs are updatedDave Borowitz2016-07-143-40/+168
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Currently, there is a race where a user of a DfsRepository in a single thread may get unexpected MissingObjectExceptions trying to look up an object that appears as the current value of a ref: 1. Thread A scans packs before scanning refs, for example by reading an object by SHA-1. 2. Thread B flushes an object and updates a ref to point to that object. 3. Thread A looks up the ref updated in (2). Since it is scanning refs for the first time, it sees the new object SHA-1. 4. Thread A tries to read the object it found in (3), using the cached pack list it got from (1). The object appears missing. Allow implementations to work around this by marking the object database's current pack list as "dirty." A dirty pack list means that DfsReader will rescan packs and try again if a requested object is missing. Implementations should mark objects as dirty any time the ref database reads or scans refs that might be newer than a previously cached pack list. Change-Id: I06c722b20c859ed1475628ec6a2f6d3d6d580700