21 #define SREC_PATH_PREFIX "srec://"
32 ut8 checksum = record_size;
33 checksum += address & 0xff;
34 checksum += (address >> 8) & 0xff;
35 checksum += (address >> 16) & 0xff;
36 checksum += address >> 24;
38 fprintf(
fd,
"S3%02x%08x", record_size, address);
45 fprintf(
fd,
"%02x\n", checksum);
56 size_t chunks_count = 0;
70 fprintf(
out,
"S00E000072697A696E2D7372656300EB\n");
74 RZ_LOG_ERROR(
"srec:write(): cannot write into buffer\n");
82 for (
size_t i = 0;
i < chunks_count;
i++) {
96 fprintf(
out,
"S70500000000FA\n");
113 return r < 0 ? -1 :
count;
138 if (!
str || *
str !=
'S') {
142 ut32 record_size = 0;
143 ut32 record_begin = 0;
144 ut32 record_addr = 0;
145 ut32 record_next = 0;
146 char record_type = 0;
160 if (sscanf(
str,
"S%c%02x", &record_type, &byte_count) != 2) {
161 RZ_LOG_ERROR(
"srec:parse(): invalid data in motorola srecord file at line %d\n",
line);
167 switch (record_type) {
170 if (sscanf(
str + 4,
"%04x", &record_addr) != 1) {
171 RZ_LOG_ERROR(
"srec:parse(): invalid header hexadecimal address 16-bit at line %d\n",
line);
174 record_addr &= 0xffff;
177 cksum += record_addr & 0xff;
178 cksum += record_addr >> 8;
181 if (sscanf(
str + 8 + (
i * 2),
"%02x", &
byte) != 1) {
182 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal value! at line %d\n",
line);
189 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
190 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal value! at line %d\n",
line);
192 }
else if (cksum !=
byte) {
193 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
197 str = strchr(
str + 1,
'S');
202 if (sscanf(
str + 4,
"%04x", &record_addr) != 1) {
203 RZ_LOG_ERROR(
"srec:parse(): invalid data hexadecimal address 16-bit at line %d\n",
line);
206 record_addr &= 0xffff;
209 cksum += record_addr & 0xff;
210 cksum += record_addr >> 8;
212 if ((record_next != record_addr) || ((record_size +
counter) >
UT16_MAX)) {
213 if (record_size && record_size <
UT16_MAX) {
215 RZ_LOG_ERROR(
"srec:parse(): cannot write buffer at 0x%x\n", record_begin);
219 record_begin = record_addr;
220 record_next = record_addr;
224 for (
i = 0;
i < byte_count - 3;
i++) {
225 if (sscanf(
str + 8 + (
i * 2),
"%02x", &
byte) != 1) {
230 record_data[record_size +
i] = (
ut8)
byte & 0xff;
238 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
241 }
else if (cksum !=
byte) {
242 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
246 str = strchr(
str + 1,
'S');
250 if (sscanf(
str + 4,
"%04x", &record_addr) != 1) {
251 RZ_LOG_ERROR(
"srec:parse(): invalid count hexadecimal address 16-bit at line %d\n",
line);
254 record_addr &= 0xffff;
257 cksum += record_addr & 0xff;
258 cksum += record_addr >> 8;
261 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
264 }
else if (cksum !=
byte) {
265 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
269 str = strchr(
str + 1,
'S');
273 if (sscanf(
str + 4,
"%04x", &record_addr) != 1) {
274 RZ_LOG_ERROR(
"srec:parse(): invalid terminator hexadecimal address 16-bit at line %d\n",
line);
277 record_addr &= 0xffff;
280 cksum += record_addr & 0xff;
281 cksum += record_addr >> 8;
284 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
287 }
else if (cksum !=
byte) {
288 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
292 str = strchr(
str + 1,
'S');
296 if (sscanf(
str + 4,
"%06x", &record_addr) != 1) {
297 RZ_LOG_ERROR(
"srec:parse(): invalid data hexadecimal address 24-bit at line %d\n",
line);
300 record_addr &= 0xffffff;
303 cksum += record_addr & 0xff;
304 cksum += (record_addr >> 8) & 0xff;
305 cksum += record_addr >> 16;
307 if ((record_next != record_addr) || ((record_size +
counter) >
UT16_MAX)) {
308 if (record_size && record_size <
UT16_MAX) {
310 RZ_LOG_ERROR(
"srec:parse(): cannot write buffer at 0x%x\n", record_begin);
314 record_begin = record_addr;
315 record_next = record_addr;
319 for (
i = 0;
i < byte_count - 4;
i++) {
320 if (sscanf(
str + 10 + (
i * 2),
"%02x", &
byte) != 1) {
325 record_data[record_size +
i] = (
ut8)
byte & 0xff;
333 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
336 }
else if (cksum !=
byte) {
337 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
341 str = strchr(
str + 1,
'S');
345 if (sscanf(
str + 4,
"%06x", &record_addr) != 1) {
346 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal address 24-bit at line %d\n",
line);
349 record_addr &= 0xffffff;
352 cksum += record_addr & 0xff;
353 cksum += (record_addr >> 8) & 0xff;
354 cksum += record_addr >> 16;
357 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
360 }
else if (cksum !=
byte) {
361 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
365 str = strchr(
str + 1,
'S');
369 if (sscanf(
str + 4,
"%06x", &record_addr) != 1) {
370 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal address 24-bit at line %d\n",
line);
373 record_addr &= 0xffffff;
375 eol = strchr(
str + 1,
'S');
381 cksum += record_addr & 0xff;
382 cksum += (record_addr >> 8) & 0xff;
383 cksum += record_addr >> 16;
386 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
389 }
else if (cksum !=
byte) {
390 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
394 str = strchr(
str + 1,
'S');
399 if (sscanf(
str + 4,
"%08x", &record_addr) != 1) {
400 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal address 32-bit at line %d\n",
line);
403 record_addr &= 0xffffffff;
405 eol = strchr(
str + 1,
'S');
411 cksum += record_addr & 0xff;
412 cksum += (record_addr >> 8) & 0xff;
413 cksum += (record_addr >> 16) & 0xff;
414 cksum += record_addr >> 24;
416 if ((record_next != record_addr) || ((record_size +
counter) >
UT16_MAX)) {
417 if (record_size && record_size <
UT16_MAX) {
419 RZ_LOG_ERROR(
"srec:parse(): cannot write buffer at 0x%x\n", record_begin);
423 record_begin = record_addr;
424 record_next = record_addr;
428 for (
i = 0;
i < byte_count - 5;
i++) {
429 if (sscanf(
str + 12 + (
i * 2),
"%02x", &
byte) != 1) {
434 record_data[record_size +
i] = (
ut8)
byte & 0xff;
442 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &
byte) != 1) {
445 }
else if (cksum !=
byte) {
446 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
450 str = strchr(
str + 1,
'S');
454 if (sscanf(
str + 4,
"%08x", &record_addr) != 1) {
455 RZ_LOG_ERROR(
"srec:parse(): invalid hexadecimal address 32-bit at line %d\n",
line);
458 record_addr &= 0xffffffff;
460 eol = strchr(
str + 1,
'S');
466 cksum += record_addr & 0xff;
467 cksum += (record_addr >> 8) & 0xff;
468 cksum += (record_addr >> 16) & 0xff;
469 cksum += record_addr >> 24;
472 if (sscanf(
str + 2 + (byte_count * 2),
"%02x", &byte) != 1) {
475 }
else if (cksum !=
byte) {
476 RZ_LOG_ERROR(
"srec:parse(): checksum check failed (got %02x expected %02x) at line %d\n",
byte, cksum,
line);
480 str = strchr(
str + 1,
'S');
486 RZ_LOG_ERROR(
"srec:parse(): invalid motorola srecord type '%c' at line %d\n", record_type,
line);
491 if (record_size && record_size <
UT16_MAX) {
493 RZ_LOG_ERROR(
"srec:parse(): cannot write buffer at 0x%x\n", record_begin);
551 .desc =
"Motorola S-record file format",
563 #ifndef RZ_PLUGIN_INCORE
const lzma_allocator const uint8_t size_t uint8_t * out
static static sync static getppid static getegid const char static filename char static len const char char static bufsiz static mask static vfork const void static prot static getpgrp const char static swapflags static arg static fd static protocol static who struct sockaddr static addrlen static backlog struct timeval struct timezone static tz const struct iovec static count static mode const void const struct sockaddr static tolen const char static pathname void count
RZ_API void Ht_() free(HtName_(Ht) *ht)
static st32 __write(RzIO *io, RzIODesc *fd, const ut8 *buf, st32 count)
static st32 __close(RzIODesc *fd)
static bool __plugin_open(RzIO *io, const char *pathname, bool many)
RzIOPlugin rz_io_plugin_srec
static bool __resize(RzIO *io, RzIODesc *fd, ut64 size)
RZ_API RzLibStruct rizin_plugin
static RzIODesc * __open(RzIO *io, const char *pathname, st32 rw, st32 mode)
static ut64 __lseek(struct rz_io_t *io, RzIODesc *fd, ut64 offset, st32 whence)
static void write_S3_record(FILE *fd, ut32 address, const ut8 *buffer, ut16 size)
static st32 __read(RzIO *io, RzIODesc *fd, ut8 *buf, st32 count)
static bool srecord_parse(RzBuffer *buf, char *str)
return memset(p, 0, total)
void * malloc(size_t size)
static static fork const void static count static fd const char const char static newpath char char char static envp time_t static t const char static mode static whence const char static dir time_t static t unsigned static seconds const char struct utimbuf static buf static inc static sig const char pathname
#define rz_return_if_fail(expr)
#define rz_return_val_if_fail(expr, val)
RZ_API bool rz_buf_resize(RZ_NONNULL RzBuffer *b, ut64 newsize)
Resize the buffer size.
RZ_API st64 rz_buf_seek(RZ_NONNULL RzBuffer *b, st64 addr, int whence)
Modify the current cursor position in the buffer.
RZ_API st64 rz_buf_write_at(RZ_NONNULL RzBuffer *b, ut64 addr, RZ_NONNULL const ut8 *buf, ut64 len)
Write len bytes of the buffer at the specified address.
RZ_API st64 rz_buf_read_at(RZ_NONNULL RzBuffer *b, ut64 addr, RZ_NONNULL RZ_OUT ut8 *buf, ut64 len)
Read len bytes of the buffer at the specified address.
RZ_API const RzBufferSparseChunk * rz_buf_sparse_get_chunks(RzBuffer *b, RZ_NONNULL size_t *count)
Only for sparse RzBuffers, get all sparse data chunks currently populated.
RZ_API void rz_buf_free(RzBuffer *b)
Free all internal data hold by the buffer and the buffer.
RZ_API RZ_OWN RzBuffer * rz_buf_new_sparse(ut8 Oxff)
Creates a sparse buffer.
RZ_API RZ_OWN char * rz_file_slurp(const char *str, RZ_NULLABLE size_t *usz)
RZ_API RzIODesc * rz_io_desc_new(RzIO *io, RzIOPlugin *plugin, const char *uri, int flags, int mode, void *data)
#define RZ_LOG_ERROR(fmtstr,...)
RZ_API FILE * rz_sys_fopen(const char *path, const char *mode)
ut8 * data
size == to - from + 1
ut64 to
inclusive, there can't be chunks with size == 0
if(dbg->bits==RZ_SYS_BITS_64)
ut64(WINAPI *w32_GetEnabledXStateFeatures)()
static const z80_opcode fd[]