1from gdbclientutils import * 2 3class TestGDBRemotePlatformFile(GDBPlatformClientTestBase): 4 5 def test_file(self): 6 """Test mock operations on a remote file""" 7 8 class Responder(MockGDBServerResponder): 9 def vFile(self, packet): 10 if packet.startswith("vFile:open:"): 11 return "F10" 12 elif packet.startswith("vFile:pread:"): 13 return "Fd;frobnicator" 14 elif packet.startswith("vFile:pwrite:"): 15 return "Fa" 16 elif packet.startswith("vFile:close:"): 17 return "F0" 18 return "F-1,58" 19 20 self.server.responder = Responder() 21 22 self.match("platform file open /some/file.txt -v 0755", 23 [r"File Descriptor = 16"]) 24 self.match("platform file read 16 -o 11 -c 13", 25 [r"Return = 11\nData = \"frobnicator\""]) 26 self.match("platform file write 16 -o 11 -d teststring", 27 [r"Return = 10"]) 28 self.match("platform file close 16", 29 [r"file 16 closed."]) 30 self.assertPacketLogContains([ 31 "vFile:open:2f736f6d652f66696c652e747874,00000202,000001ed", 32 "vFile:pread:10,d,b", 33 "vFile:pwrite:10,b,teststring", 34 "vFile:close:10", 35 ]) 36 37 def test_file_fail(self): 38 """Test mocked failures of remote operations""" 39 40 class Responder(MockGDBServerResponder): 41 def vFile(self, packet): 42 # use ENOSYS as this constant differs between GDB Remote 43 # Protocol and Linux, so we can test the translation 44 return "F-1,58" 45 46 self.server.responder = Responder() 47 48 self.match("platform file open /some/file.txt -v 0755", 49 [r"error: Function not implemented"], 50 error=True) 51 self.match("platform file read 16 -o 11 -c 13", 52 [r"error: Function not implemented"], 53 error=True) 54 self.match("platform file write 16 -o 11 -d teststring", 55 [r"error: Function not implemented"], 56 error=True) 57 self.match("platform file close 16", 58 [r"error: Function not implemented"], 59 error=True) 60 self.assertPacketLogContains([ 61 "vFile:open:2f736f6d652f66696c652e747874,00000202,000001ed", 62 "vFile:pread:10,d,b", 63 "vFile:pwrite:10,b,teststring", 64 "vFile:close:10", 65 ]) 66 67 def test_file_size(self): 68 """Test 'platform get-size'""" 69 70 class Responder(MockGDBServerResponder): 71 def vFile(self, packet): 72 return "F1000" 73 74 self.server.responder = Responder() 75 76 self.match("platform get-size /some/file.txt", 77 [r"File size of /some/file\.txt \(remote\): 4096"]) 78 self.assertPacketLogContains([ 79 "vFile:size:2f736f6d652f66696c652e747874", 80 ]) 81 82 def test_file_size_fallback(self): 83 """Test 'platform get-size fallback to vFile:fstat'""" 84 85 class Responder(MockGDBServerResponder): 86 def vFile(self, packet): 87 if packet.startswith("vFile:open:"): 88 return "F5" 89 elif packet.startswith("vFile:fstat:"): 90 return "F40;" + 28 * "\0" + "\0\0\0\0\0\1\2\3" + 28 * "\0" 91 if packet.startswith("vFile:close:"): 92 return "F0" 93 return "" 94 95 self.server.responder = Responder() 96 97 self.match("platform get-size /some/file.txt", 98 [r"File size of /some/file\.txt \(remote\): 66051"]) 99 self.assertPacketLogContains([ 100 "vFile:size:2f736f6d652f66696c652e747874", 101 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000", 102 "vFile:fstat:5", 103 "vFile:close:5", 104 ]) 105 106 def test_file_permissions(self): 107 """Test 'platform get-permissions'""" 108 109 class Responder(MockGDBServerResponder): 110 def vFile(self, packet): 111 return "F1a4" 112 113 self.server.responder = Responder() 114 115 self.match("platform get-permissions /some/file.txt", 116 [r"File permissions of /some/file\.txt \(remote\): 0o0644"]) 117 self.assertPacketLogContains([ 118 "vFile:mode:2f736f6d652f66696c652e747874", 119 ]) 120 121 def test_file_permissions_fallback(self): 122 """Test 'platform get-permissions' fallback to fstat""" 123 124 class Responder(MockGDBServerResponder): 125 def vFile(self, packet): 126 if packet.startswith("vFile:open:"): 127 return "F5" 128 elif packet.startswith("vFile:fstat:"): 129 return "F40;" + 8 * "\0" + "\0\0\1\xA4" + 52 * "\0" 130 if packet.startswith("vFile:close:"): 131 return "F0" 132 return "" 133 134 self.server.responder = Responder() 135 136 try: 137 self.match("platform get-permissions /some/file.txt", 138 [r"File permissions of /some/file\.txt \(remote\): 0o0644"]) 139 self.assertPacketLogContains([ 140 "vFile:mode:2f736f6d652f66696c652e747874", 141 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000", 142 "vFile:fstat:5", 143 "vFile:close:5", 144 ]) 145 finally: 146 self.dbg.GetSelectedPlatform().DisconnectRemote() 147 148 def test_file_exists(self): 149 """Test 'platform file-exists'""" 150 151 class Responder(MockGDBServerResponder): 152 def vFile(self, packet): 153 return "F,1" 154 155 self.server.responder = Responder() 156 157 self.match("platform file-exists /some/file.txt", 158 [r"File /some/file\.txt \(remote\) exists"]) 159 self.assertPacketLogContains([ 160 "vFile:exists:2f736f6d652f66696c652e747874", 161 ]) 162 163 def test_file_exists_not(self): 164 """Test 'platform file-exists' with non-existing file""" 165 166 class Responder(MockGDBServerResponder): 167 def vFile(self, packet): 168 return "F,0" 169 170 self.server.responder = Responder() 171 172 self.match("platform file-exists /some/file.txt", 173 [r"File /some/file\.txt \(remote\) does not exist"]) 174 self.assertPacketLogContains([ 175 "vFile:exists:2f736f6d652f66696c652e747874", 176 ]) 177 178 def test_file_exists_fallback(self): 179 """Test 'platform file-exists' fallback to open""" 180 181 class Responder(MockGDBServerResponder): 182 def vFile(self, packet): 183 if packet.startswith("vFile:open:"): 184 return "F5" 185 if packet.startswith("vFile:close:"): 186 return "F0" 187 return "" 188 189 self.server.responder = Responder() 190 191 self.match("platform file-exists /some/file.txt", 192 [r"File /some/file\.txt \(remote\) exists"]) 193 self.assertPacketLogContains([ 194 "vFile:exists:2f736f6d652f66696c652e747874", 195 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000", 196 "vFile:close:5", 197 ]) 198 199 def test_file_exists_not_fallback(self): 200 """Test 'platform file-exists' fallback to open with non-existing file""" 201 202 class Responder(MockGDBServerResponder): 203 def vFile(self, packet): 204 if packet.startswith("vFile:open:"): 205 return "F-1,2" 206 return "" 207 208 self.server.responder = Responder() 209 210 self.match("platform file-exists /some/file.txt", 211 [r"File /some/file\.txt \(remote\) does not exist"]) 212 self.assertPacketLogContains([ 213 "vFile:exists:2f736f6d652f66696c652e747874", 214 "vFile:open:2f736f6d652f66696c652e747874,00000000,00000000", 215 ]) 216