OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "bin/file.h" | 5 #include "bin/file.h" |
6 | 6 |
7 #include "bin/builtin.h" | 7 #include "bin/builtin.h" |
8 #include "bin/dartutils.h" | 8 #include "bin/dartutils.h" |
9 #include "bin/io_buffer.h" | 9 #include "bin/io_buffer.h" |
10 #include "bin/thread.h" | 10 #include "bin/thread.h" |
(...skipping 192 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
203 } else { | 203 } else { |
204 OSError os_error(-1, "Invalid argument", OSError::kUnknown); | 204 OSError os_error(-1, "Invalid argument", OSError::kUnknown); |
205 Dart_Handle err = DartUtils::NewDartOSError(&os_error); | 205 Dart_Handle err = DartUtils::NewDartOSError(&os_error); |
206 if (Dart_IsError(err)) Dart_PropagateError(err); | 206 if (Dart_IsError(err)) Dart_PropagateError(err); |
207 Dart_SetReturnValue(args, err); | 207 Dart_SetReturnValue(args, err); |
208 } | 208 } |
209 Dart_ExitScope(); | 209 Dart_ExitScope(); |
210 } | 210 } |
211 | 211 |
212 | 212 |
213 void FUNCTION_NAME(File_ReadList)(Dart_NativeArguments args) { | 213 void FUNCTION_NAME(File_ReadInto)(Dart_NativeArguments args) { |
214 Dart_EnterScope(); | 214 Dart_EnterScope(); |
215 File* file = GetFilePointer(Dart_GetNativeArgument(args, 0)); | 215 File* file = GetFilePointer(Dart_GetNativeArgument(args, 0)); |
216 ASSERT(file != NULL); | 216 ASSERT(file != NULL); |
217 Dart_Handle buffer_obj = Dart_GetNativeArgument(args, 1); | 217 Dart_Handle buffer_obj = Dart_GetNativeArgument(args, 1); |
218 ASSERT(Dart_IsList(buffer_obj)); | 218 ASSERT(Dart_IsList(buffer_obj)); |
219 // Offset and length arguments are checked in Dart code to be | 219 // start and end arguments are checked in Dart code to be |
220 // integers and have the property that (offset + length) <= | 220 // integers and have the property that end <= |
221 // list.length. Therefore, it is safe to extract their value as | 221 // list.length. Therefore, it is safe to extract their value as |
222 // intptr_t. | 222 // intptr_t. |
223 intptr_t offset = | 223 intptr_t start = |
224 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 2)); | 224 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 2)); |
225 intptr_t length = | 225 intptr_t end = |
226 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 3)); | 226 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 3)); |
| 227 intptr_t length = end - start; |
227 intptr_t array_len = 0; | 228 intptr_t array_len = 0; |
228 Dart_Handle result = Dart_ListLength(buffer_obj, &array_len); | 229 Dart_Handle result = Dart_ListLength(buffer_obj, &array_len); |
229 if (Dart_IsError(result)) Dart_PropagateError(result); | 230 if (Dart_IsError(result)) Dart_PropagateError(result); |
230 ASSERT((offset + length) <= array_len); | 231 ASSERT(end <= array_len); |
231 uint8_t* buffer = new uint8_t[length]; | 232 uint8_t* buffer = new uint8_t[length]; |
232 int64_t bytes_read = file->Read(reinterpret_cast<void*>(buffer), length); | 233 int64_t bytes_read = file->Read(reinterpret_cast<void*>(buffer), length); |
233 if (bytes_read >= 0) { | 234 if (bytes_read >= 0) { |
234 result = Dart_ListSetAsBytes(buffer_obj, offset, buffer, bytes_read); | 235 result = Dart_ListSetAsBytes(buffer_obj, start, buffer, bytes_read); |
235 if (Dart_IsError(result)) { | 236 if (Dart_IsError(result)) { |
236 delete[] buffer; | 237 delete[] buffer; |
237 Dart_PropagateError(result); | 238 Dart_PropagateError(result); |
238 } | 239 } |
239 Dart_SetReturnValue(args, Dart_NewInteger(bytes_read)); | 240 Dart_SetReturnValue(args, Dart_NewInteger(bytes_read)); |
240 } else { | 241 } else { |
241 Dart_Handle err = DartUtils::NewDartOSError(); | 242 Dart_Handle err = DartUtils::NewDartOSError(); |
242 if (Dart_IsError(err)) Dart_PropagateError(err); | 243 if (Dart_IsError(err)) Dart_PropagateError(err); |
243 Dart_SetReturnValue(args, err); | 244 Dart_SetReturnValue(args, err); |
244 } | 245 } |
245 delete[] buffer; | 246 delete[] buffer; |
246 Dart_ExitScope(); | 247 Dart_ExitScope(); |
247 } | 248 } |
248 | 249 |
249 | 250 |
250 void FUNCTION_NAME(File_WriteList)(Dart_NativeArguments args) { | 251 void FUNCTION_NAME(File_WriteFrom)(Dart_NativeArguments args) { |
251 Dart_EnterScope(); | 252 Dart_EnterScope(); |
252 File* file = GetFilePointer(Dart_GetNativeArgument(args, 0)); | 253 File* file = GetFilePointer(Dart_GetNativeArgument(args, 0)); |
253 ASSERT(file != NULL); | 254 ASSERT(file != NULL); |
254 Dart_Handle buffer_obj = Dart_GetNativeArgument(args, 1); | 255 Dart_Handle buffer_obj = Dart_GetNativeArgument(args, 1); |
255 ASSERT(Dart_IsList(buffer_obj)); | 256 ASSERT(Dart_IsList(buffer_obj)); |
256 // Offset and length arguments are checked in Dart code to be | 257 // Offset and length arguments are checked in Dart code to be |
257 // integers and have the property that (offset + length) <= | 258 // integers and have the property that (offset + length) <= |
258 // list.length. Therefore, it is safe to extract their value as | 259 // list.length. Therefore, it is safe to extract their value as |
259 // intptr_t. | 260 // intptr_t. |
260 intptr_t offset = | 261 intptr_t start = |
261 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 2)); | 262 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 2)); |
262 intptr_t length = | 263 intptr_t end = |
263 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 3)); | 264 DartUtils::GetIntptrValue(Dart_GetNativeArgument(args, 3)); |
| 265 intptr_t length = end - start; |
264 intptr_t buffer_len = 0; | 266 intptr_t buffer_len = 0; |
265 Dart_Handle result = Dart_ListLength(buffer_obj, &buffer_len); | 267 Dart_Handle result = Dart_ListLength(buffer_obj, &buffer_len); |
266 if (Dart_IsError(result)) Dart_PropagateError(result); | 268 if (Dart_IsError(result)) Dart_PropagateError(result); |
267 ASSERT((offset + length) <= buffer_len); | 269 ASSERT(end <= buffer_len); |
268 uint8_t* buffer = new uint8_t[length]; | 270 uint8_t* buffer = new uint8_t[length]; |
269 result = Dart_ListGetAsBytes(buffer_obj, offset, buffer, length); | 271 result = Dart_ListGetAsBytes(buffer_obj, start, buffer, length); |
270 if (Dart_IsError(result)) { | 272 if (Dart_IsError(result)) { |
271 delete[] buffer; | 273 delete[] buffer; |
272 Dart_PropagateError(result); | 274 Dart_PropagateError(result); |
273 } | 275 } |
274 int64_t bytes_written = file->Write(reinterpret_cast<void*>(buffer), length); | 276 int64_t bytes_written = file->Write(reinterpret_cast<void*>(buffer), length); |
275 if (bytes_written >= 0) { | 277 if (bytes_written != length) { |
276 Dart_SetReturnValue(args, Dart_NewInteger(bytes_written)); | |
277 } else { | |
278 Dart_Handle err = DartUtils::NewDartOSError(); | 278 Dart_Handle err = DartUtils::NewDartOSError(); |
279 if (Dart_IsError(err)) Dart_PropagateError(err); | 279 if (Dart_IsError(err)) Dart_PropagateError(err); |
280 Dart_SetReturnValue(args, err); | 280 Dart_SetReturnValue(args, err); |
281 } | 281 } |
282 delete[] buffer; | 282 delete[] buffer; |
283 Dart_ExitScope(); | 283 Dart_ExitScope(); |
284 } | 284 } |
285 | 285 |
286 | 286 |
287 void FUNCTION_NAME(File_Position)(Dart_NativeArguments args) { | 287 void FUNCTION_NAME(File_Position)(Dart_NativeArguments args) { |
(...skipping 638 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
926 return CObject::NewOSError(); | 926 return CObject::NewOSError(); |
927 } | 927 } |
928 } else { | 928 } else { |
929 return CObject::FileClosedError(); | 929 return CObject::FileClosedError(); |
930 } | 930 } |
931 } | 931 } |
932 return CObject::IllegalArgumentError(); | 932 return CObject::IllegalArgumentError(); |
933 } | 933 } |
934 | 934 |
935 | 935 |
936 static CObject* FileReadListRequest(const CObjectArray& request) { | 936 static CObject* FileReadIntoRequest(const CObjectArray& request) { |
937 if (request.Length() == 3 && | 937 if (request.Length() == 3 && |
938 request[1]->IsIntptr() && | 938 request[1]->IsIntptr() && |
939 request[2]->IsInt32OrInt64()) { | 939 request[2]->IsInt32OrInt64()) { |
940 File* file = CObjectToFilePointer(request[1]); | 940 File* file = CObjectToFilePointer(request[1]); |
941 ASSERT(file != NULL); | 941 ASSERT(file != NULL); |
942 if (!file->IsClosed()) { | 942 if (!file->IsClosed()) { |
943 int64_t length = CObjectInt32OrInt64ToInt64(request[2]); | 943 int64_t length = CObjectInt32OrInt64ToInt64(request[2]); |
944 Dart_CObject* io_buffer = CObject::NewIOBuffer(length); | 944 Dart_CObject* io_buffer = CObject::NewIOBuffer(length); |
945 uint8_t* data = io_buffer->value.as_external_typed_data.data; | 945 uint8_t* data = io_buffer->value.as_external_typed_data.data; |
946 int64_t bytes_read = file->Read(data, length); | 946 int64_t bytes_read = file->Read(data, length); |
(...skipping 27 matching lines...) Expand all Loading... |
974 case Dart_CObject::kUint16Array: | 974 case Dart_CObject::kUint16Array: |
975 return 2; | 975 return 2; |
976 default: | 976 default: |
977 break; | 977 break; |
978 } | 978 } |
979 UNREACHABLE(); | 979 UNREACHABLE(); |
980 return -1; | 980 return -1; |
981 } | 981 } |
982 | 982 |
983 | 983 |
984 static CObject* FileWriteListRequest(const CObjectArray& request) { | 984 static CObject* FileWriteFromRequest(const CObjectArray& request) { |
985 if (request.Length() == 5 && | 985 if (request.Length() == 5 && |
986 request[1]->IsIntptr() && | 986 request[1]->IsIntptr() && |
987 (request[2]->IsTypedData() || request[2]->IsArray()) && | 987 (request[2]->IsTypedData() || request[2]->IsArray()) && |
988 request[3]->IsInt32OrInt64() && | 988 request[3]->IsInt32OrInt64() && |
989 request[4]->IsInt32OrInt64()) { | 989 request[4]->IsInt32OrInt64()) { |
990 File* file = CObjectToFilePointer(request[1]); | 990 File* file = CObjectToFilePointer(request[1]); |
991 ASSERT(file != NULL); | 991 ASSERT(file != NULL); |
992 if (!file->IsClosed()) { | 992 if (!file->IsClosed()) { |
993 int64_t offset = CObjectInt32OrInt64ToInt64(request[3]); | 993 int64_t start = CObjectInt32OrInt64ToInt64(request[3]); |
994 int64_t length = CObjectInt32OrInt64ToInt64(request[4]); | 994 int64_t end = CObjectInt32OrInt64ToInt64(request[4]); |
| 995 int64_t length = end - start; |
995 uint8_t* buffer_start; | 996 uint8_t* buffer_start; |
996 if (request[2]->IsTypedData()) { | 997 if (request[2]->IsTypedData()) { |
997 CObjectTypedData typed_data(request[2]); | 998 CObjectTypedData typed_data(request[2]); |
998 offset = offset * SizeInBytes(typed_data.Type()); | 999 start = start * SizeInBytes(typed_data.Type()); |
999 length = length * SizeInBytes(typed_data.Type()); | 1000 length = length * SizeInBytes(typed_data.Type()); |
1000 buffer_start = typed_data.Buffer() + offset; | 1001 buffer_start = typed_data.Buffer() + start; |
1001 } else { | 1002 } else { |
1002 CObjectArray array(request[2]); | 1003 CObjectArray array(request[2]); |
1003 buffer_start = new uint8_t[length]; | 1004 buffer_start = new uint8_t[length]; |
1004 for (int i = 0; i < length; i++) { | 1005 for (int i = 0; i < length; i++) { |
1005 if (array[i + offset]->IsInt32OrInt64()) { | 1006 if (array[i + start]->IsInt32OrInt64()) { |
1006 int64_t value = CObjectInt32OrInt64ToInt64(array[i + offset]); | 1007 int64_t value = CObjectInt32OrInt64ToInt64(array[i + start]); |
1007 buffer_start[i] = static_cast<uint8_t>(value & 0xFF); | 1008 buffer_start[i] = static_cast<uint8_t>(value & 0xFF); |
1008 } else { | 1009 } else { |
1009 // Unsupported type. | 1010 // Unsupported type. |
1010 delete[] buffer_start; | 1011 delete[] buffer_start; |
1011 return CObject::IllegalArgumentError(); | 1012 return CObject::IllegalArgumentError(); |
1012 } | 1013 } |
1013 } | 1014 } |
1014 offset = 0; | 1015 start = 0; |
1015 } | 1016 } |
1016 int64_t bytes_written = | 1017 int64_t bytes_written = |
1017 file->Write(reinterpret_cast<void*>(buffer_start), length); | 1018 file->Write(reinterpret_cast<void*>(buffer_start), length); |
1018 if (!request[2]->IsTypedData()) { | 1019 if (!request[2]->IsTypedData()) { |
1019 delete[] buffer_start; | 1020 delete[] buffer_start; |
1020 } | 1021 } |
1021 if (bytes_written >= 0) { | 1022 if (bytes_written >= 0) { |
1022 return new CObjectInt64(CObject::NewInt64(bytes_written)); | 1023 return new CObjectInt64(CObject::NewInt64(bytes_written)); |
1023 } else { | 1024 } else { |
1024 return CObject::NewOSError(); | 1025 return CObject::NewOSError(); |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1114 break; | 1115 break; |
1115 case File::kReadByteRequest: | 1116 case File::kReadByteRequest: |
1116 response = FileReadByteRequest(request); | 1117 response = FileReadByteRequest(request); |
1117 break; | 1118 break; |
1118 case File::kWriteByteRequest: | 1119 case File::kWriteByteRequest: |
1119 response = FileWriteByteRequest(request); | 1120 response = FileWriteByteRequest(request); |
1120 break; | 1121 break; |
1121 case File::kReadRequest: | 1122 case File::kReadRequest: |
1122 response = FileReadRequest(request); | 1123 response = FileReadRequest(request); |
1123 break; | 1124 break; |
1124 case File::kReadListRequest: | 1125 case File::kReadIntoRequest: |
1125 response = FileReadListRequest(request); | 1126 response = FileReadIntoRequest(request); |
1126 break; | 1127 break; |
1127 case File::kWriteListRequest: | 1128 case File::kWriteFromRequest: |
1128 response = FileWriteListRequest(request); | 1129 response = FileWriteFromRequest(request); |
1129 break; | 1130 break; |
1130 case File::kDeleteLinkRequest: | 1131 case File::kDeleteLinkRequest: |
1131 response = FileDeleteLinkRequest(request); | 1132 response = FileDeleteLinkRequest(request); |
1132 break; | 1133 break; |
1133 case File::kCreateLinkRequest: | 1134 case File::kCreateLinkRequest: |
1134 response = FileCreateLinkRequest(request); | 1135 response = FileCreateLinkRequest(request); |
1135 break; | 1136 break; |
1136 default: | 1137 default: |
1137 UNREACHABLE(); | 1138 UNREACHABLE(); |
1138 } | 1139 } |
(...skipping 13 matching lines...) Expand all Loading... |
1152 Dart_EnterScope(); | 1153 Dart_EnterScope(); |
1153 Dart_SetReturnValue(args, Dart_Null()); | 1154 Dart_SetReturnValue(args, Dart_Null()); |
1154 Dart_Port service_port = File::GetServicePort(); | 1155 Dart_Port service_port = File::GetServicePort(); |
1155 if (service_port != ILLEGAL_PORT) { | 1156 if (service_port != ILLEGAL_PORT) { |
1156 // Return a send port for the service port. | 1157 // Return a send port for the service port. |
1157 Dart_Handle send_port = Dart_NewSendPort(service_port); | 1158 Dart_Handle send_port = Dart_NewSendPort(service_port); |
1158 Dart_SetReturnValue(args, send_port); | 1159 Dart_SetReturnValue(args, send_port); |
1159 } | 1160 } |
1160 Dart_ExitScope(); | 1161 Dart_ExitScope(); |
1161 } | 1162 } |
OLD | NEW |