From 5e66f1ef654c488fac4f8d3ec357f31470ef2504 Mon Sep 17 00:00:00 2001 From: Richard Cornwell Date: Sun, 17 Nov 2019 12:43:20 -0500 Subject: [PATCH] SCP: Updated to current. --- scp.c | 16 ++++++++++++++-- sim_card.c | 18 +++++++++--------- sim_disk.c | 28 ++++++++++++---------------- sim_serial.c | 2 +- sim_tape.c | 50 +++++++++++++++++++++++++++++++++++++++----------- 5 files changed, 75 insertions(+), 39 deletions(-) diff --git a/scp.c b/scp.c index 3a7c098..762e7eb 100644 --- a/scp.c +++ b/scp.c @@ -2865,7 +2865,8 @@ fprintf (st, " HELP dev SET\n"); fprintf (st, " HELP dev SHOW\n"); fprintf (st, " HELP dev REGISTERS\n\n"); fprintf (st, "Help is available for the following commands:\n\n "); -qsort (hlp_cmdp, cmd_cnt, sizeof(*hlp_cmdp), _cmd_name_compare); +if (hlp_cmdp) + qsort (hlp_cmdp, cmd_cnt, sizeof(*hlp_cmdp), _cmd_name_compare); line_offset = 4; for (i=0; iname, st); @@ -5713,9 +5714,10 @@ return SCPE_OK; const char *sprint_capac (DEVICE *dptr, UNIT *uptr) { -static char capac_buf[((CHAR_BIT * sizeof (t_value) * 4 + 3)/3) + 8]; +static char capac_buf[((CHAR_BIT * sizeof (t_value) * 4 + 3)/3) + 12]; t_addr kval = (uptr->flags & UNIT_BINK)? 1024: 1000; t_addr mval; +double remfrac; t_addr psize = uptr->capac; const char *scale, *width; @@ -5730,18 +5732,28 @@ else width = "B"; if ((psize < (kval * 10)) && (0 != (psize % kval))) { + remfrac = 0.0; scale = ""; } else if ((psize < (mval * 10)) && (0 != (psize % mval))){ scale = "K"; + remfrac = ((double)(psize % kval))/kval; psize = psize / kval; } else { scale = "M"; + remfrac = ((double)(psize % mval))/mval; psize = psize / mval; } sprint_val (capac_buf, (t_value) psize, 10, T_ADDR_W, PV_LEFT); +if ((remfrac != 0.0) && (sim_switches & SWMASK ('R'))) { + char *plast_char = &capac_buf[strlen (capac_buf) - 1]; + char save_char = *plast_char; + + sprintf (plast_char, "%0.3f", remfrac); + *plast_char = save_char; + } sprintf (&capac_buf[strlen (capac_buf)], "%s%s", scale, width); return capac_buf; } diff --git a/sim_card.c b/sim_card.c index f33e7dd..0923bb2 100644 --- a/sim_card.c +++ b/sim_card.c @@ -599,12 +599,12 @@ sim_card_eof(UNIT *uptr) struct _card_buffer { - char buffer[8192+500]; /* Buffer data */ + uint8 buffer[8192+500]; /* Buffer data */ int len; /* Amount of data in buffer */ int size; /* Size of last card read */ }; -static int _cmpcard(const char *p, const char *s) { +static int _cmpcard(const uint8 *p, const char *s) { int i; if (p[0] != '~') return 0; @@ -629,7 +629,7 @@ _sim_parse_card(UNIT *uptr, DEVICE *dptr, struct _card_buffer *buf, uint16 (*ima /* Check buffer to see if binary card in it. */ for (i = 0, temp = 0; i < 160 && i len; i+=2) - temp |= buf->buffer[i]; + temp |= (uint16)(buf->buffer[i] & 0xFF); /* Check if every other char < 16 & full buffer */ if ((temp & 0x0f) == 0 && i == 160) mode = MODE_BIN; /* Probably binary */ @@ -789,9 +789,9 @@ _sim_parse_card(UNIT *uptr, DEVICE *dptr, struct _card_buffer *buf, uint16 (*ima } /* Move data to buffer */ for (col = i = 0; i < 160;) { - temp |= buf->buffer[i]; + temp |= (uint16)(buf->buffer[i] & 0xff); (*image)[col] = (buf->buffer[i++] >> 4) & 0xF; - (*image)[col++] |= ((uint16)buf->buffer[i++]) << 4; + (*image)[col++] |= ((uint16)buf->buffer[i++] & 0xf) << 4; } /* Check if format error */ if (temp & 0xF) @@ -802,8 +802,8 @@ _sim_parse_card(UNIT *uptr, DEVICE *dptr, struct _card_buffer *buf, uint16 (*ima case MODE_CBN: sim_debug(DEBUG_CARD, dptr, "cbn\n"); /* Check if first character is a tape mark */ - if (((uint8)buf->buffer[0]) == 0217 && - (buf->len == 1 || (((uint8)buf->buffer[1]) & 0200) != 0)) { + if (buf->buffer[0] == 0217 && + (buf->len == 1 || (buf->buffer[1] & 0200) != 0)) { i = 1; (*image)[0] |= CARD_EOF; break; @@ -844,7 +844,7 @@ _sim_parse_card(UNIT *uptr, DEVICE *dptr, struct _card_buffer *buf, uint16 (*ima case MODE_BCD: sim_debug(DEBUG_CARD, dptr, "bcd ["); /* Check if first character is a tape mark */ - if (((uint8)buf->buffer[0]) == 0217 && (((uint8)buf->buffer[1]) & 0200) != 0) { + if (buf->buffer[0] == 0217 && (buf->buffer[1] & 0200) != 0) { i = 1; (*image)[0] |= CARD_EOF; break; @@ -885,7 +885,7 @@ _sim_parse_card(UNIT *uptr, DEVICE *dptr, struct _card_buffer *buf, uint16 (*ima (*image)[0] |= CARD_ERR; /* Move data to buffer */ for (i = 0; i < 80 && i < buf->len; i++) { - temp = buf->buffer[i] & 0xFF; + temp = (uint16)(buf->buffer[i]) & 0xFF; (*image)[i] = ebcdic_to_hol[temp]; } break; diff --git a/sim_disk.c b/sim_disk.c index df3183d..1c8a2a2 100644 --- a/sim_disk.c +++ b/sim_disk.c @@ -1110,8 +1110,7 @@ static t_offset get_ods2_filesystem_size (UNIT *uptr) DEVICE *dptr; t_addr saved_capac; struct disk_context *ctx = (struct disk_context *)uptr->disk_ctx; -t_offset temp_capac = 512 * (t_offset)0xFFFFFFFFu; /* Make sure we can access the largest sector */ -uint32 capac_factor; +t_offset temp_capac = (sim_toffset_64 ? (t_addr)0xFFFFFFFFu : (t_addr)0x7FFFFFFFu); /* Make sure we can access the largest sector */ ODS2_HomeBlock Home; ODS2_FileHeader Header; ODS2_Retreval *Retr; @@ -1123,9 +1122,8 @@ t_seccnt sects_read; if ((dptr = find_dev_from_unit (uptr)) == NULL) return ret_val; -capac_factor = ((dptr->dwidth / dptr->aincr) == 16) ? 2 : 1; /* save capacity units (word: 2, byte: 1) */ saved_capac = uptr->capac; -uptr->capac = (t_addr)(temp_capac/(capac_factor*((dptr->flags & DEV_SECTORS) ? 512 : 1))); +uptr->capac = temp_capac; if ((sim_disk_rdsect (uptr, 512 / ctx->sector_size, (uint8 *)&Home, §s_read, sizeof (Home) / ctx->sector_size)) || (sects_read != (sizeof (Home) / ctx->sector_size))) goto Return_Cleanup; @@ -1197,8 +1195,7 @@ static t_offset get_ods1_filesystem_size (UNIT *uptr) DEVICE *dptr; t_addr saved_capac; struct disk_context *ctx = (struct disk_context *)uptr->disk_ctx; -t_offset temp_capac = 512 * (t_offset)0xFFFFFFFFu; /* Make sure we can access the largest sector */ -uint32 capac_factor; +t_addr temp_capac = (sim_toffset_64 ? (t_addr)0xFFFFFFFFu : (t_addr)0x7FFFFFFFu); /* Make sure we can access the largest sector */ ODS1_HomeBlock Home; ODS1_FileHeader Header; ODS1_Retreval *Retr; @@ -1211,9 +1208,8 @@ t_seccnt sects_read; if ((dptr = find_dev_from_unit (uptr)) == NULL) return ret_val; -capac_factor = ((dptr->dwidth / dptr->aincr) == 16) ? 2 : 1; /* save capacity units (word: 2, byte: 1) */ saved_capac = uptr->capac; -uptr->capac = (t_addr)(temp_capac/(capac_factor*((dptr->flags & DEV_SECTORS) ? 512 : 1))); +uptr->capac = temp_capac; if ((sim_disk_rdsect (uptr, 512 / ctx->sector_size, (uint8 *)&Home, §s_read, sizeof (Home) / ctx->sector_size)) || (sects_read != (sizeof (Home) / ctx->sector_size))) goto Return_Cleanup; @@ -1274,8 +1270,7 @@ static t_offset get_ultrix_filesystem_size (UNIT *uptr) DEVICE *dptr; t_addr saved_capac; struct disk_context *ctx = (struct disk_context *)uptr->disk_ctx; -t_offset temp_capac = 512 * (t_offset)0xFFFFFFFFu; /* Make sure we can access the largest sector */ -uint32 capac_factor; +t_addr temp_capac = (sim_toffset_64 ? (t_addr)0xFFFFFFFFu : (t_addr)0x7FFFFFFFu); /* Make sure we can access the largest sector */ uint8 sector_buf[512]; ultrix_disklabel *Label = (ultrix_disklabel *)(sector_buf + sizeof (sector_buf) - sizeof (ultrix_disklabel)); t_offset ret_val = (t_offset)-1; @@ -1285,9 +1280,8 @@ t_seccnt sects_read; if ((dptr = find_dev_from_unit (uptr)) == NULL) return ret_val; -capac_factor = ((dptr->dwidth / dptr->aincr) == 16) ? 2 : 1; /* save capacity units (word: 2, byte: 1) */ saved_capac = uptr->capac; -uptr->capac = (t_addr)(temp_capac/(capac_factor*((dptr->flags & DEV_SECTORS) ? 512 : 1))); +uptr->capac = temp_capac; if ((sim_disk_rdsect (uptr, 31 * (512 / ctx->sector_size), sector_buf, §s_read, 512 / ctx->sector_size)) || (sects_read != (512 / ctx->sector_size))) goto Return_Cleanup; @@ -1393,8 +1387,7 @@ static t_offset get_rt11_filesystem_size (UNIT *uptr) DEVICE *dptr; t_addr saved_capac; struct disk_context *ctx = (struct disk_context *)uptr->disk_ctx; -t_offset temp_capac = 512 * (t_offset)0xFFFFFFFFu; -uint32 capac_factor; +t_addr temp_capac = (sim_toffset_64 ? (t_addr)0xFFFFFFFFu : (t_addr)0x7FFFFFFFu); /* Make sure we can access the largest sector */ uint8 sector_buf[1024]; RT11_HomeBlock Home; t_seccnt sects_read; @@ -1409,9 +1402,8 @@ t_offset ret_val = (t_offset)-1; if ((dptr = find_dev_from_unit (uptr)) == NULL) return ret_val; -capac_factor = ((dptr->dwidth / dptr->aincr) == 16) ? 2 : 1; saved_capac = uptr->capac; -uptr->capac = (t_addr)(temp_capac / (capac_factor * ((dptr->flags & DEV_SECTORS) ? 512 : 1))); +uptr->capac = temp_capac; for (part = 0; part < RT11_MAXPARTITIONS; part++) { uint16 seg_highest; @@ -2018,10 +2010,14 @@ if (container_size && (container_size != (t_offset)-1)) { if ((container_size < current_unit_size) && ((DKUF_F_VHD == DK_GET_FMT (uptr)) || (0 != (uptr->flags & UNIT_RO)))) { if (!sim_quiet) { + int32 saved_switches = sim_switches; + + sim_switches = SWMASK ('R'); uptr->capac = (t_addr)(container_size/(ctx->capac_factor*((dptr->flags & DEV_SECTORS) ? 512 : 1))); sim_printf ("%s%d: non expandable disk container '%s' is smaller than simulated device (%s < ", sim_dname (dptr), (int)(uptr-dptr->units), cptr, sprint_capac (dptr, uptr)); uptr->capac = saved_capac; sim_printf ("%s)\n", sprint_capac (dptr, uptr)); + sim_switches = saved_switches; } sim_disk_detach (uptr); return SCPE_OPENERR; diff --git a/sim_serial.c b/sim_serial.c index dc13960..86ae870 100644 --- a/sim_serial.c +++ b/sim_serial.c @@ -448,8 +448,8 @@ return port; void sim_close_serial (SERHANDLE port) { -sim_close_os_serial (port); _serial_remove_from_open_list (port); +sim_close_os_serial (port); } t_stat sim_config_serial (SERHANDLE port, CONST char *sconfig) diff --git a/sim_tape.c b/sim_tape.c index 8729a89..89cd09e 100644 --- a/sim_tape.c +++ b/sim_tape.c @@ -598,6 +598,16 @@ if (MT_GET_FMT (uptr) < MTUF_F_ANSI) fflush (uptr->fileref); } +static const char *_sim_tape_format_name (UNIT *uptr) +{ +int32 f = MT_GET_FMT (uptr); + +if (f == MTUF_F_ANSI) + return ansi_args[MT_GET_ANSI_TYP (uptr)].name; +else + return fmts[f].name; +} + /* Attach tape unit */ t_stat sim_tape_attach (UNIT *uptr, CONST char *cptr) @@ -662,6 +672,7 @@ switch (MT_GET_FMT (uptr)) { if (1) { const char *ocptr = cptr; char label[CBUFSIZE] = "simh"; + int file_errors = 0; if ((MT_GET_ANSI_TYP (uptr) == MTAT_F_RT11) || (MT_GET_ANSI_TYP (uptr) == MTAT_F_RSX11) || @@ -678,10 +689,16 @@ switch (MT_GET_FMT (uptr)) { if (!uptr->fileref) return SCPE_MEM; while (*cptr != 0) { /* do all mods */ + uint32 initial_file_count = tape->file_count; + cptr = get_glyph_nc (cptr, gbuf, ','); /* get filename */ - sim_dir_scan (gbuf, sim_tape_add_ansi_entry, tape); + r = sim_dir_scan (gbuf, sim_tape_add_ansi_entry, tape); + if (r != SCPE_OK) + sim_messagef (SCPE_ARG, "file not found: %s\n", gbuf); + if (tape->file_count == initial_file_count) + ++file_errors; } - if (tape->file_count > 0) { + if ((tape->file_count > 0) && (file_errors == 0)) { r = SCPE_OK; memory_tape_add_block (tape, NULL, 0); /* Tape Mark */ uptr->flags |= UNIT_ATT; @@ -693,6 +710,7 @@ switch (MT_GET_FMT (uptr)) { r = SCPE_ARG; memory_free_tape (uptr->fileref); uptr->fileref = NULL; + cptr = ocptr; } } break; @@ -798,11 +816,12 @@ switch (MT_GET_FMT (uptr)) { break; } if (r != SCPE_OK) { /* error? */ + r = sim_messagef (r, "Can't open %s format tape image: %s\n", _sim_tape_format_name (uptr), cptr); if (auto_format) /* format was specified at attach time? */ sim_tape_set_fmt (uptr, 0, "SIMH", NULL); /* restore default format */ uptr->recsize = 0; uptr->tape_eom = 0; - return sim_messagef (r, "Can't open tape image: %s\n", cptr); + return r; } if ((sim_switches & SWMASK ('D')) && !had_debug) { @@ -3220,12 +3239,7 @@ return sim_messagef (SCPE_ARG, "Unknown tape format: %s\n", cptr); t_stat sim_tape_show_fmt (FILE *st, UNIT *uptr, int32 val, CONST void *desc) { -int32 f = MT_GET_FMT (uptr); - -if (f == MTUF_F_ANSI) - fprintf (st, "%s format", ansi_args[MT_GET_ANSI_TYP (uptr)].name); -else - fprintf (st, "%s format", fmts[f].name); +fprintf (st, "%s format", _sim_tape_format_name (uptr)); return SCPE_OK; } @@ -4232,7 +4246,7 @@ static void ansi_fill_text_buffer (FILE *f, char *buf, size_t buf_size, size_t r if (rec_size >= record_skip_ending) rec_size -= record_skip_ending; if ((rec_size + 4) > (int)(buf_size - offset)) { /* room for record? */ - fseek (f, start, SEEK_SET); + (void)fseek (f, start, SEEK_SET); break; } sprintf (rec_size_str, "%04u", (int)(rec_size + 4)); @@ -4387,6 +4401,7 @@ return tape; static int ansi_add_file_to_tape (MEMORY_TAPE *tape, const char *filename) { FILE *f; +struct stat statb; struct ansi_tape_parameters *ansi = &ansi_args[tape->ansi_type]; uint8 *block = NULL; size_t max_record_size; @@ -4401,9 +4416,22 @@ HDR2 hdr2; HDR3 hdr3; HDR4 hdr4; +memset (&statb, 0, sizeof (statb)); +if (stat (filename, &statb)) { + sim_printf ("Can't stat: %s\n", filename); + return -1; + } +if (S_IFDIR & statb.st_mode) { + sim_printf ("Can't put a directory on tape: %s\n", filename); + return -1; + } +if (!(S_IFREG & statb.st_mode)) { + sim_printf ("Can't put a non regular file on tape: %s\n", filename); + return -1; + } f = fopen (filename, "rb"); if (f == NULL) { - fprintf (stderr, "Can't open: %s - %s\n", filename, strerror(errno)); + sim_printf ("Can't open: %s - %s\n", filename, strerror(errno)); return errno; } tape_classify_file_contents (f, &max_record_size, &lf_line_endings, &crlf_line_endings);