288 lines · python
1from lldbsuite.test.gdbclientutils import *2from lldbsuite.test.decorators import *3from lldbsuite.test.lldbgdbclient import GDBPlatformClientTestBase4 5 6class TestGDBRemotePlatformFile(GDBPlatformClientTestBase):7 def test_file(self):8 """Test mock operations on a remote file"""9 10 class Responder(MockGDBServerResponder):11 def vFile(self, packet):12 if packet.startswith("vFile:open:"):13 return "F10"14 elif packet.startswith("vFile:pread:"):15 return "Fd;frobnicator"16 elif packet.startswith("vFile:pwrite:"):17 return "Fa"18 elif packet.startswith("vFile:close:"):19 return "F0"20 return "F-1,58"21 22 self.server.responder = Responder()23 24 self.match(25 "platform file open /some/file.txt -v 0755", [r"File Descriptor = 16"]26 )27 self.match(28 "platform file read 16 -o 11 -c 13",29 [r"Return = 11\nData = \"frobnicator\""],30 )31 self.match("platform file write 16 -o 11 -d teststring", [r"Return = 10"])32 self.match("platform file close 16", [r"file 16 closed."])33 self.assertPacketLogReceived(34 [35 "vFile:open:2f736f6d652f66696c652e747874,00000202,000001ed",36 "vFile:pread:10,d,b",37 "vFile:pwrite:10,b,teststring",38 "vFile:close:10",39 ]40 )41 42 def test_file_fail(self):43 """Test mocked failures of remote operations"""44 45 class Responder(MockGDBServerResponder):46 def vFile(self, packet):47 # use ENOSYS as this constant differs between GDB Remote48 # Protocol and Linux, so we can test the translation49 return "F-1,58"50 51 self.server.responder = Responder()52 enosys_regex = r"error: (Function not implemented|function not supported)"53 self.match(54 "platform file open /some/file.txt -v 0755",55 [enosys_regex],56 error=True,57 )58 self.match(59 "platform file read 16 -o 11 -c 13",60 [enosys_regex],61 error=True,62 )63 self.match(64 "platform file write 16 -o 11 -d teststring",65 [enosys_regex],66 error=True,67 )68 self.match("platform file close 16", [enosys_regex], error=True)69 self.assertPacketLogReceived(70 [71 "vFile:open:2f736f6d652f66696c652e747874,00000202,000001ed",72 "vFile:pread:10,d,b",73 "vFile:pwrite:10,b,teststring",74 "vFile:close:10",75 ]76 )77 78 def test_file_size(self):79 """Test 'platform get-size'"""80 81 class Responder(MockGDBServerResponder):82 def vFile(self, packet):83 return "F1000"84 85 self.server.responder = Responder()86 87 self.match(88 "platform get-size /some/file.txt",89 [r"File size of /some/file\.txt \(remote\): 4096"],90 )91 self.assertPacketLogReceived(92 [93 "vFile:size:2f736f6d652f66696c652e747874",94 ]95 )96 97 def test_file_size_fallback(self):98 """Test 'platform get-size fallback to vFile:fstat'"""99 100 class Responder(MockGDBServerResponder):101 def vFile(self, packet):102 if packet.startswith("vFile:open:"):103 return "F5"104 elif packet.startswith("vFile:fstat:"):105 return "F40;" + 28 * "\0" + "\0\0\0\0\0\1\2\3" + 28 * "\0"106 if packet.startswith("vFile:close:"):107 return "F0"108 return ""109 110 self.server.responder = Responder()111 112 self.match(113 "platform get-size /some/file.txt",114 [r"File size of /some/file\.txt \(remote\): 66051"],115 )116 self.assertPacketLogReceived(117 [118 "vFile:size:2f736f6d652f66696c652e747874",119 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000",120 "vFile:fstat:5",121 "vFile:close:5",122 ]123 )124 125 self.runCmd("platform disconnect")126 127 # For a new onnection, we should attempt vFile:size once again.128 server2 = MockGDBServer(self.server_socket_class())129 server2.responder = Responder()130 server2.start()131 self.addTearDownHook(lambda: server2.stop())132 self.runCmd("platform connect " + server2.get_connect_url())133 self.match(134 "platform get-size /other/file.txt",135 [r"File size of /other/file\.txt \(remote\): 66051"],136 )137 138 self.assertPacketLogReceived(139 [140 "vFile:size:2f6f746865722f66696c652e747874",141 "vFile:open:2f6f746865722f66696c652e747874,00000000,00000000",142 "vFile:fstat:5",143 "vFile:close:5",144 ],145 log=server2.responder.packetLog,146 )147 148 @expectedFailureAll(149 hostoslist=["windows"], bugnumber="github.com/llvm/llvm-project/issues/92255"150 )151 def test_file_permissions(self):152 """Test 'platform get-permissions'"""153 154 class Responder(MockGDBServerResponder):155 def vFile(self, packet):156 return "F1a4"157 158 self.server.responder = Responder()159 160 self.match(161 "platform get-permissions /some/file.txt",162 [r"File permissions of /some/file\.txt \(remote\): 0o0644"],163 )164 self.assertPacketLogReceived(165 [166 "vFile:mode:2f736f6d652f66696c652e747874",167 ]168 )169 170 @expectedFailureAll(171 hostoslist=["windows"], bugnumber="github.com/llvm/llvm-project/issues/92255"172 )173 def test_file_permissions_fallback(self):174 """Test 'platform get-permissions' fallback to fstat"""175 176 class Responder(MockGDBServerResponder):177 def vFile(self, packet):178 if packet.startswith("vFile:open:"):179 return "F5"180 elif packet.startswith("vFile:fstat:"):181 return "F40;" + 8 * "\0" + "\0\0\1\xA4" + 52 * "\0"182 if packet.startswith("vFile:close:"):183 return "F0"184 return ""185 186 self.server.responder = Responder()187 188 try:189 self.match(190 "platform get-permissions /some/file.txt",191 [r"File permissions of /some/file\.txt \(remote\): 0o0644"],192 )193 self.assertPacketLogReceived(194 [195 "vFile:mode:2f736f6d652f66696c652e747874",196 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000",197 "vFile:fstat:5",198 "vFile:close:5",199 ]200 )201 finally:202 self.dbg.GetSelectedPlatform().DisconnectRemote()203 204 def test_file_exists(self):205 """Test 'platform file-exists'"""206 207 class Responder(MockGDBServerResponder):208 def vFile(self, packet):209 return "F,1"210 211 self.server.responder = Responder()212 213 self.match(214 "platform file-exists /some/file.txt",215 [r"File /some/file\.txt \(remote\) exists"],216 )217 self.assertPacketLogReceived(218 [219 "vFile:exists:2f736f6d652f66696c652e747874",220 ]221 )222 223 def test_file_exists_not(self):224 """Test 'platform file-exists' with non-existing file"""225 226 class Responder(MockGDBServerResponder):227 def vFile(self, packet):228 return "F,0"229 230 self.server.responder = Responder()231 232 self.match(233 "platform file-exists /some/file.txt",234 [r"File /some/file\.txt \(remote\) does not exist"],235 )236 self.assertPacketLogReceived(237 [238 "vFile:exists:2f736f6d652f66696c652e747874",239 ]240 )241 242 def test_file_exists_fallback(self):243 """Test 'platform file-exists' fallback to open"""244 245 class Responder(MockGDBServerResponder):246 def vFile(self, packet):247 if packet.startswith("vFile:open:"):248 return "F5"249 if packet.startswith("vFile:close:"):250 return "F0"251 return ""252 253 self.server.responder = Responder()254 255 self.match(256 "platform file-exists /some/file.txt",257 [r"File /some/file\.txt \(remote\) exists"],258 )259 self.assertPacketLogReceived(260 [261 "vFile:exists:2f736f6d652f66696c652e747874",262 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000",263 "vFile:close:5",264 ]265 )266 267 def test_file_exists_not_fallback(self):268 """Test 'platform file-exists' fallback to open with non-existing file"""269 270 class Responder(MockGDBServerResponder):271 def vFile(self, packet):272 if packet.startswith("vFile:open:"):273 return "F-1,2"274 return ""275 276 self.server.responder = Responder()277 278 self.match(279 "platform file-exists /some/file.txt",280 [r"File /some/file\.txt \(remote\) does not exist"],281 )282 self.assertPacketLogReceived(283 [284 "vFile:exists:2f736f6d652f66696c652e747874",285 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000",286 ]287 )288