1
2
3
4
5
6
7
8
9
10
11 package org.eclipse.jgit.http.test;
12
13 import static org.junit.Assert.assertEquals;
14 import static org.junit.Assert.assertTrue;
15
16 import java.io.ByteArrayOutputStream;
17 import java.io.IOException;
18 import java.io.InputStream;
19 import java.io.OutputStream;
20 import java.net.HttpURLConnection;
21 import java.net.URL;
22
23 import javax.servlet.http.HttpServletRequest;
24
25 import org.eclipse.jetty.servlet.ServletContextHandler;
26 import org.eclipse.jetty.servlet.ServletHolder;
27 import org.eclipse.jgit.errors.RepositoryNotFoundException;
28 import org.eclipse.jgit.http.server.GitServlet;
29 import org.eclipse.jgit.http.server.GitSmartHttpTools;
30 import org.eclipse.jgit.internal.JGitText;
31 import org.eclipse.jgit.junit.TestRepository;
32 import org.eclipse.jgit.junit.http.HttpTestCase;
33 import org.eclipse.jgit.lib.Constants;
34 import org.eclipse.jgit.lib.ObjectId;
35 import org.eclipse.jgit.lib.Repository;
36 import org.eclipse.jgit.lib.StoredConfig;
37 import org.eclipse.jgit.revwalk.RevBlob;
38 import org.eclipse.jgit.transport.PacketLineIn;
39 import org.eclipse.jgit.transport.PacketLineOut;
40 import org.eclipse.jgit.transport.URIish;
41 import org.eclipse.jgit.util.NB;
42 import org.junit.Before;
43 import org.junit.Test;
44
45 public class ProtocolErrorTest extends HttpTestCase {
46 private Repository remoteRepository;
47
48 private URIish remoteURI;
49
50 private RevBlob a_blob;
51
52 @Override
53 @Before
54 public void setUp() throws Exception {
55 super.setUp();
56
57 final TestRepository<Repository> src = createTestRepository();
58 final String srcName = src.getRepository().getDirectory().getName();
59
60 ServletContextHandler app = server.addContext("/git");
61 GitServlet gs = new GitServlet();
62 gs.setRepositoryResolver((HttpServletRequest req, String name) -> {
63 if (!name.equals(srcName)) {
64 throw new RepositoryNotFoundException(name);
65 }
66 final Repository db = src.getRepository();
67 db.incrementOpen();
68 return db;
69 });
70 app.addServlet(new ServletHolder(gs), "/*");
71
72 server.setUp();
73
74 remoteRepository = src.getRepository();
75 remoteURI = toURIish(app, srcName);
76
77 StoredConfig cfg = remoteRepository.getConfig();
78 cfg.setBoolean("http", null, "receivepack", true);
79 cfg.save();
80
81 a_blob = src.blob("a");
82 }
83
84 @Test
85 public void testPush_UnpackError_TruncatedPack() throws Exception {
86 StringBuilder sb = new StringBuilder();
87 sb.append(ObjectId.zeroId().name());
88 sb.append(' ');
89 sb.append(a_blob.name());
90 sb.append(' ');
91 sb.append("refs/objects/A");
92 sb.append('\0');
93 sb.append("report-status");
94
95 ByteArrayOutputStream reqbuf = new ByteArrayOutputStream();
96 PacketLineOut reqpck = new PacketLineOut(reqbuf);
97 reqpck.writeString(sb.toString());
98 reqpck.end();
99
100 packHeader(reqbuf, 1);
101
102 byte[] reqbin = reqbuf.toByteArray();
103
104 URL u = new URL(remoteURI.toString() + "/git-receive-pack");
105 HttpURLConnection c = (HttpURLConnection) u.openConnection();
106 try {
107 c.setRequestMethod("POST");
108 c.setDoOutput(true);
109 c.setRequestProperty("Content-Type",
110 GitSmartHttpTools.RECEIVE_PACK_REQUEST_TYPE);
111 c.setFixedLengthStreamingMode(reqbin.length);
112 try (OutputStream out = c.getOutputStream()) {
113 out.write(reqbin);
114 }
115
116 assertEquals(200, c.getResponseCode());
117 assertEquals(GitSmartHttpTools.RECEIVE_PACK_RESULT_TYPE,
118 c.getContentType());
119
120 try (InputStream rawin = c.getInputStream()) {
121 PacketLineIn pckin = new PacketLineIn(rawin);
122 assertEquals("unpack error "
123 + JGitText.get().packfileIsTruncatedNoParam,
124 pckin.readString());
125 assertEquals("ng refs/objects/A n/a (unpacker error)",
126 pckin.readString());
127 assertTrue(PacketLineIn.isEnd(pckin.readString()));
128 }
129 } finally {
130 c.disconnect();
131 }
132 }
133
134 private static void packHeader(ByteArrayOutputStream tinyPack, int cnt)
135 throws IOException {
136 final byte[] hdr = new byte[8];
137 NB.encodeInt32(hdr, 0, 2);
138 NB.encodeInt32(hdr, 4, cnt);
139
140 tinyPack.write(Constants.PACK_SIGNATURE);
141 tinyPack.write(hdr, 0, 8);
142 }
143 }