abcdisk.c 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770
  1. /*
  2. * abcdisk.c
  3. *
  4. * Emulate an ABC80/800 disk controller
  5. */
  6. #include <string.h>
  7. #include <stdio.h>
  8. #include "fw.h"
  9. #include "io.h"
  10. #include "abcio.h"
  11. #include "console.h"
  12. #include "sdcard.h"
  13. #include "ff.h"
  14. /* Option flags, mostly for debugging */
  15. #define NOTTHERE 0
  16. #define READONLY 0
  17. #define INTERLEAVE 0
  18. #define FORMAT_SUPPORT 0
  19. enum drive_flags {
  20. DF_MOUNTED = 1, /* Host file open, drive exported */
  21. DF_READONLY = 2, /* Drive is readonly */
  22. DF_DISABLED = 4, /* Drive is disabled */
  23. DF_DIRTY = 8 /* Disk has been written */
  24. };
  25. enum pending {
  26. PEND_IO = 1,
  27. PEND_RESET = 2
  28. };
  29. /* Number of fragments (extents) we can memoize */
  30. #define MAX_FAST_FRAGMENTS 16
  31. #define CLTBL_SIZE ((MAX_FAST_FRAGMENTS+1)*2)
  32. /* Per-drive state */
  33. struct drive_state {
  34. FIL file; /* Host file */
  35. char name[4]; /* Drive name */
  36. uint16_t sectors; /* Total size in 256-byte sectors */
  37. #if INTERLEAVE
  38. uint8_t ilmsk, ilfac; /* Software interleaving parameters */
  39. #endif
  40. enum drive_flags flags;
  41. enum drive_flags force; /* Option to force flags */
  42. DWORD cltbl[CLTBL_SIZE]; /* Extent map */
  43. };
  44. /* Fixed parameters for each controller */
  45. struct ctl_params {
  46. uint8_t clustshift; /* log2(clustersize/256) */
  47. uint8_t devsel; /* I/O device select */
  48. uint16_t maxsectors; /* Maximum sectors for this controller */
  49. uint8_t c, h, s; /* Disk geometry */
  50. bool newaddr; /* "New addressing" */
  51. const char name[4]; /* Name of controller (disk type) */
  52. #if INTERLEAVE
  53. uint8_t ilmsk, ilfac; /* Software interleaving parea */
  54. #endif
  55. #if FORMAT_SUPPORT
  56. bool fmtdata_i_buf; /* Use user-provided formatting data */
  57. #endif
  58. } __attribute__((aligned(4)));
  59. /* Per-controller state */
  60. struct ctl_state {
  61. struct abc_dev iodev;
  62. const struct ctl_params *params;
  63. uint8_t k[4]; /* Command bytes */
  64. uint8_t drives; /* Total drives present */
  65. bool initialized; /* Controller initialized */
  66. volatile enum pending pending; /* Need to do I/O */
  67. struct drive_state drv[8]; /* Per-drive state */
  68. uint8_t buf[4][256]; /* 4 host buffers @ 256 bytes */
  69. };
  70. /*
  71. * DOSGEN depends on this value... and different DOSGEN
  72. * expect different values. If this value is wrong, DOSGEN
  73. * will spin forever on "testing sector..."
  74. */
  75. #define OUT_OF_RANGE 0x21 /* Status code for an invalid sector */
  76. #define DISK_NOT_READY 0x80
  77. #define WRITE_PROTECT 0x40
  78. #define WRITE_FAULT 0x20
  79. #define CRC_ERROR 0x08
  80. enum controller_types {
  81. MOx,
  82. MFx,
  83. SFx,
  84. HDx,
  85. CONTROLLER_TYPES
  86. };
  87. #if INTERLEAVE
  88. # define IL(mask, fac) .ilmsk = (mask), .ilfac = (fac),
  89. #else
  90. # define IL(mask, fac)
  91. #endif
  92. static const struct ctl_params parameters[CONTROLLER_TYPES] = {
  93. /*
  94. * MOx: covers all of these formats:
  95. * SSSD = 40×8×1 (80K, FD2/DD80),
  96. * SSDD = 40×16×1 (160K, FD2D/DD82/ABC830) and
  97. * DSDD = 40×16×2 (320K, FD4D/DD84/DD52)
  98. */
  99. [MOx] = {
  100. .devsel = 45,
  101. .clustshift = 0,
  102. .maxsectors = 40 * 2 * 16,
  103. .c = 40, .h = 2, .s = 16,
  104. .name = "mo",
  105. #if FORMAT_SUPPORT
  106. .fmtdata_in_buf = true,
  107. #endif
  108. IL(15, 7)
  109. },
  110. /* MFx: DSQD = 80×16x2 (640K, ABC832/834) */
  111. [MFx] = {
  112. .devsel = 44,
  113. .clustshift = 2,
  114. .maxsectors = 80 * 2 * 16,
  115. .c = 80, .h = 2, .s = 16,
  116. .name = "mf"
  117. },
  118. /* SFx: 8" floppy (DD88, ABC838) */
  119. [SFx] = {
  120. .devsel = 46,
  121. .clustshift = 2,
  122. .maxsectors = (77 * 2 - 1) * 26, /* Track 0, side 0 not used */
  123. .c = 77, .h = 2, .s = 26,
  124. .name = "sf"
  125. },
  126. [HDx] = {
  127. .devsel = 36,
  128. .clustshift = 5,
  129. .newaddr = true, /* Actually irrelevant for clustshift = 5 */
  130. .maxsectors = (239 * 8 - 1) * 32, /* Maximum supported by UFD-DOS */
  131. .c = 238, .h = 16, .s = 64,
  132. .name = "hd"
  133. }
  134. };
  135. static struct ctl_state __dram_bss controllers[CONTROLLER_TYPES];
  136. static inline bool mounted(const struct drive_state *drv)
  137. {
  138. return !!(drv->flags & DF_MOUNTED);
  139. }
  140. static inline struct drive_state *cur_drv_mutable(struct ctl_state *state)
  141. {
  142. return &state->drv[state->k[1] & 7];
  143. }
  144. static inline const struct drive_state *cur_drv(const struct ctl_state *state)
  145. {
  146. return &state->drv[state->k[1] & 7];
  147. }
  148. static inline unsigned int cur_sector(const struct ctl_state *state)
  149. {
  150. uint8_t k2 = state->k[2], k3 = state->k[3];
  151. if (state->params->newaddr)
  152. return (k2 << 8) + k3;
  153. else
  154. return (((k2 << 3) + (k3 >> 5)) << state->params->clustshift)
  155. + (k3 & 31);
  156. }
  157. /* Get physical sector number, after interleaving */
  158. static inline unsigned int
  159. virt2phys(const struct drive_state *drv, unsigned int sector)
  160. {
  161. #if INTERLEAVE
  162. unsigned int ilmsk = drv->ilmsk;
  163. unsigned int ilfac = drv->ilfac;
  164. sector = (sector & ~ilmsk) | ((sector * ilfac) & ilmsk);
  165. #endif
  166. return sector;
  167. }
  168. static inline unsigned int phys_sector(const struct ctl_state *state)
  169. {
  170. return virt2phys(cur_drv(state), cur_sector(state));
  171. }
  172. static inline unsigned int file_pos(const struct ctl_state *state)
  173. {
  174. return phys_sector(state) << 8;
  175. }
  176. static inline bool file_pos_valid(const struct ctl_state *state)
  177. {
  178. return phys_sector(state) < cur_drv(state)->sectors;
  179. }
  180. static inline bool cur_sector_valid(const struct ctl_state *state)
  181. {
  182. uint8_t k3 = state->k[3];
  183. if (!state->params->newaddr && ((k3 & 31) >> state->params->clustshift))
  184. return false;
  185. return phys_sector(state) < state->params->maxsectors;
  186. }
  187. static inline uint8_t *cur_buf(struct ctl_state *state)
  188. {
  189. return state->buf[state->k[1] >> 6];
  190. }
  191. static void disk_start_command(struct ctl_state *state)
  192. {
  193. #if 0
  194. con_printf("%-2s: start command\n", state->params->name);
  195. #endif
  196. memset(&state->k, 0xee, sizeof state->k);
  197. abc_setup_out_queue(&state->iodev, state->k, 4, 0x81);
  198. }
  199. static void sync_drives(struct ctl_state *state)
  200. {
  201. for (int i = 0; i < 8; i++) {
  202. struct drive_state *drv = &state->drv[i];
  203. if (drv->flags & DF_DIRTY) {
  204. f_sync(&state->drv[i].file);
  205. drv->flags &= ~DF_DIRTY;
  206. }
  207. }
  208. }
  209. static void disk_set_error(struct ctl_state *state, unsigned int error)
  210. {
  211. abc_set_inp_default(&state->iodev, error);
  212. }
  213. static void disk_reset_state(struct ctl_state *state)
  214. {
  215. abc_set_inp_status(&state->iodev, 0);
  216. disk_set_error(state, 0);
  217. sync_drives(state);
  218. disk_start_command(state);
  219. }
  220. static struct drive_state *
  221. name_to_drive(const char *drive)
  222. {
  223. struct ctl_state *state;
  224. unsigned int ndrive;
  225. /* All drive names are three letters long */
  226. if (strlen(drive) != 3)
  227. return NULL;
  228. ndrive = drive[2] - '0';
  229. if (ndrive > 7)
  230. return NULL;
  231. if (!memcmp("dr", drive, 2)) {
  232. /* DRx alias for MOx (matches "old DOS") */
  233. return &controllers[MOx].drv[ndrive];
  234. }
  235. for (int i = 0; i < CONTROLLER_TYPES; i++) {
  236. struct ctl_state *state = &controllers[i];
  237. if (!memcmp(state->params->name, drive, 2))
  238. return &state->drv[ndrive];
  239. }
  240. return NULL; /* No such disk */
  241. }
  242. bool valid_drive_name(const char *drive)
  243. {
  244. return name_to_drive(drive) != NULL;
  245. }
  246. static int mount_drive(struct drive_state *drv, struct ctl_state *state,
  247. const char *filename)
  248. {
  249. FRESULT rv;
  250. if (mounted(drv)) {
  251. if (!(sdc.fsstatus & STA_NOINIT))
  252. f_close(&drv->file);
  253. drv->flags &= ~DF_MOUNTED;
  254. state->drives--;
  255. }
  256. if (drv->force & DF_DISABLED)
  257. return -1;
  258. drv->flags = drv->force & ~DF_MOUNTED;
  259. if (!filename) {
  260. return 0; /* Explicit unmount */
  261. } else {
  262. while (1) {
  263. BYTE mode = FA_OPEN_EXISTING | FA_READ;
  264. if (!(drv->flags & DF_READONLY))
  265. mode |= FA_WRITE;
  266. rv = f_open(&drv->file, filename, mode);
  267. if (rv == FR_WRITE_PROTECTED && (mode & FA_WRITE)) {
  268. drv->flags |= DF_READONLY;
  269. continue;
  270. }
  271. drv->flags |= (rv == FR_OK) ? DF_MOUNTED : DF_DISABLED;
  272. break;
  273. }
  274. if (!(drv->flags & DF_MOUNTED))
  275. return -1;
  276. }
  277. con_printf("abcdisk: %-3s = %s\n", drv->name, filename);
  278. /* Try to memoize extents for fast seek */
  279. drv->cltbl[0] = CLTBL_SIZE;
  280. drv->file.cltbl = drv->cltbl;
  281. rv = f_lseek(&drv->file, CREATE_LINKMAP);
  282. if (rv != FR_OK) {
  283. con_printf("abcdisk: %-3s ! file too fragmented, will be slow\n",
  284. drv->name);
  285. }
  286. /*
  287. * Smaller than the standard disk size? Treat the sectors
  288. * beyond the end as bad.
  289. */
  290. unsigned int filesec = f_size(&drv->file) >> 8;
  291. drv->sectors = min(filesec, state->params->maxsectors);
  292. /* Interleaving parameters */
  293. #if INTERLEAVE
  294. drv->ilfac = state->params->ilfac;
  295. drv->ilmsk = state->params->ilmsk;
  296. #endif
  297. state->drives++;
  298. return 0;
  299. }
  300. static void unmount_drives(struct ctl_state *state)
  301. {
  302. int i;
  303. for (int i = 0; i < 8; i++) {
  304. struct drive_state *drv = &state->drv[i];
  305. if (drv->flags & DF_MOUNTED)
  306. mount_drive(drv, state, NULL);
  307. }
  308. }
  309. #define IDLE_CALLBACK_MASK (1 << 4) /* C3 = reset */
  310. static void abcdisk_callback_out(struct abc_dev *dev, uint8_t data)
  311. {
  312. struct ctl_state *state = container_of(dev, struct ctl_state, iodev);
  313. dev->callback_mask = IDLE_CALLBACK_MASK;
  314. ABC_INP1_DATA = dev->inp_data[1] = 0;
  315. state->pending |= PEND_IO;
  316. }
  317. static void abcdisk_callback_inp(struct abc_dev *dev)
  318. {
  319. struct ctl_state *state = container_of(dev, struct ctl_state, iodev);
  320. dev->callback_mask = IDLE_CALLBACK_MASK;
  321. ABC_INP1_DATA = dev->inp_data[1] = 0;
  322. state->pending |= PEND_IO;
  323. }
  324. static void abcdisk_callback_cmd(struct abc_dev *dev, uint8_t data, uint8_t addr)
  325. {
  326. struct ctl_state *state = container_of(dev, struct ctl_state, iodev);
  327. if (addr == 4)
  328. state->pending |= PEND_RESET;
  329. }
  330. static char abcdisk_80_800[] = "/abcdisk.800/";
  331. static const char * const disk_pfx[] = {
  332. abcdisk_80_800, "/abcdisk/", "/abcdisk.", "/", NULL
  333. };
  334. static void init_drives(struct ctl_state *state)
  335. {
  336. uint32_t abc_status = ABC_STATUS;
  337. char *p80;
  338. int i;
  339. /* .80/ or .800/ for the first entry */
  340. p80 = abcdisk_80_800 + 10 + !!(abc_status & ABC_STATUS_800);
  341. p80[0] = '0';
  342. p80[1] = '/';
  343. p80[2] = '\0';
  344. for (i = 0; i < 8; i++) {
  345. struct drive_state *drv = &state->drv[i];
  346. unsigned int filesec;
  347. const char * const *pfx;
  348. snprintf(drv->name, sizeof drv->name, "%-.2s%c",
  349. state->params->name, i + '0');
  350. for (pfx = disk_pfx; *pfx; pfx++) {
  351. char filename_buf[64];
  352. snprintf(filename_buf, sizeof filename_buf,
  353. "%s%s", *pfx, drv->name);
  354. if (!mount_drive(drv, state, filename_buf))
  355. break;
  356. }
  357. }
  358. state->initialized = true;
  359. }
  360. static void do_next_command(struct ctl_state *state)
  361. {
  362. struct drive_state *drv = cur_drv_mutable(state);
  363. uint8_t *buf = cur_buf(state);
  364. #if 0
  365. con_printf("%-3s: cmd %02x %02x %02x %02x\n",
  366. drv->name, state->k[0], state->k[1],
  367. state->k[2], state->k[3]);
  368. #endif
  369. if (state->k[0] & 0x01) {
  370. /* READ SECTOR */
  371. if (!(drv->flags & DF_MOUNTED)) {
  372. disk_set_error(state, DISK_NOT_READY);
  373. } else if (!cur_sector_valid(state)) {
  374. disk_set_error(state, OUT_OF_RANGE);
  375. } else if (!file_pos_valid(state)) {
  376. disk_set_error(state, CRC_ERROR);
  377. } else {
  378. UINT rlen = 0;
  379. FRESULT rv;
  380. set_led(LED_DISKIO, true);
  381. rv = f_lseek(&drv->file, file_pos(state));
  382. if (rv == FR_OK)
  383. rv = f_read(&drv->file, buf, 256, &rlen);
  384. if (rv != FR_OK || rlen != 256) {
  385. disk_set_error(state, CRC_ERROR);
  386. }
  387. }
  388. state->k[0] &= ~0x01; /* Command done */
  389. }
  390. if (state->k[0] & 0x02) {
  391. /* SECTOR TO HOST */
  392. state->k[0] &= ~0x02; /* Command done */
  393. abc_setup_inp_queue(&state->iodev, buf, 256, 0x01);
  394. return;
  395. }
  396. if (state->k[0] & 0x04) {
  397. /* SECTOR FROM HOST */
  398. state->k[0] &= ~0x04; /* Command done */
  399. abc_setup_out_queue(&state->iodev, buf, 256, 0x01);
  400. return;
  401. }
  402. if (state->k[0] & 0x08) {
  403. /* WRITE SECTOR */
  404. if (!(drv->flags & DF_MOUNTED)) {
  405. disk_set_error(state, DISK_NOT_READY);
  406. } else if (drv->flags & DF_READONLY) {
  407. disk_set_error(state, WRITE_PROTECT);
  408. } else if (!cur_sector_valid(state)) {
  409. disk_set_error(state, OUT_OF_RANGE);
  410. } else if (!file_pos_valid(state)) {
  411. disk_set_error(state, CRC_ERROR);
  412. } else {
  413. UINT wlen = 0;
  414. FRESULT rv;
  415. set_led(LED_DISKIO, true);
  416. rv = f_lseek(&drv->file, file_pos(state));
  417. if (rv == FR_OK) {
  418. drv->flags |= DF_DIRTY;
  419. rv = f_write(&drv->file, buf, 256, &wlen);
  420. }
  421. if (rv != FR_OK || wlen != 256)
  422. disk_set_error(state, WRITE_FAULT);
  423. }
  424. state->k[0] &= ~0x08; /* Command done */
  425. }
  426. #if FORMAT_SUPPORT
  427. /* This code needs additional work */
  428. if (state->k[0] & 0x10 && state->k[1] & 0x08) {
  429. state->out_ptr = 0;
  430. /* FORMAT */
  431. if (!drv->hf) {
  432. state->error = 0x80; /* Not ready */
  433. } else if (!file_wrok(hf)) {
  434. state->error = 0x40; /* Write protect */
  435. } else {
  436. unsigned int s, c0, c1, s0, s1;
  437. unsigned int cylsec = state->s * state->h;
  438. uint8_t data[256];
  439. unsigned int fmtsec, filesec;
  440. /* Sector count produced by format */
  441. fmtsec = state->params->maxsectors;
  442. /* For non-MO-drives, this seems to be internally generated */
  443. memset(data, 0x40, 256);
  444. if (state->fmtdata_in_buf) {
  445. /*
  446. * MO drives put the sector image in the buffers, for
  447. * backwards compatibility and to support single density.
  448. *
  449. * Right before the F7 header CRC opcode is a density byte;
  450. * 00 for single, and 01 for double. The data begins after
  451. * a byte of FB.
  452. */
  453. bool single = false;
  454. const uint8_t *p, *ep;
  455. ep = state->buf[1];
  456. for (p = state->buf[0]+1; p < ep; p++) {
  457. if (*p == 0xf7)
  458. single = (p[-1] == 0);
  459. if (*p == 0xfb)
  460. break;
  461. }
  462. fmtsec >>= single;
  463. if (*p++ == 0xfb) { /* Data block found */
  464. if (single) {
  465. /* Really two 128-byte sectors! */
  466. memcpy(data, p, 128);
  467. memcpy(data+128, p, 128);
  468. } else {
  469. memcpy(data, p, 256);
  470. }
  471. }
  472. }
  473. /*
  474. * Adjust the size of the accessible device to the smallest
  475. * of the physical file and the formatted size
  476. */
  477. filesec = drv->hf->filesize >> 8;
  478. drv->sectors = (filesec && filesec < fmtsec) ? filesec : fmtsec;
  479. /*
  480. * k2 and k3 contain the first and last cylinder numbers to
  481. * format, inclusively. The last cylinder may be partial due
  482. * to virtual remapping, e.g. for sf floppies.
  483. */
  484. c0 = state->k[2];
  485. s0 = c0 * cylsec;
  486. c1 = state->k[3] + 1;
  487. s1 = c1 * cylsec;
  488. if (tracing(TRACE_DISK)) {
  489. fprintf(tracef, "%s: formatting cyl %u..%u, sectors %u..%u\n",
  490. drv->name, c0, c1-1, s0, s1-1);
  491. }
  492. clearerr(hf->f);
  493. state->error = 0;
  494. for (s = s0; s < s1; s++) {
  495. unsigned int ps = virt2phys(drv, s);
  496. if (ps >= drv->sectors) {
  497. state->error |= 0x02; /* Track 0/Lost data? */
  498. break;
  499. } else if (hf->map) {
  500. memcpy(hf->map + (ps << 8), data, 256);
  501. } else {
  502. fseek(hf->f, ps << 8, SEEK_SET);
  503. fwrite(data, 1, 256, hf->f);
  504. }
  505. }
  506. if (ferror(hf->f))
  507. state->error |= 0x20; /* Write fault */
  508. }
  509. state->k[1] &= ~0x08;
  510. }
  511. if (!(state->k[1] & 0x38))
  512. state->k[0] &= ~0x10;
  513. #else
  514. /* No FORMAT support */
  515. state->k[0] &= ~0x10;
  516. #endif
  517. state->k[0] &= ~0xe0; /* Unimplemented commands */
  518. disk_start_command(state);
  519. }
  520. static FATFS sd_fs;
  521. static int mount_disk(void)
  522. {
  523. FRESULT rv;
  524. char label[128];
  525. uint32_t volid, freeclust;
  526. FATFS *fs;
  527. set_led(LED_DISKIO, true);
  528. rv = f_mount(&sd_fs, "", 1);
  529. if (rv != FR_OK) {
  530. con_printf("sdcard: no volume found\n");
  531. set_led(LED_DISKIO, false);
  532. return -1;
  533. }
  534. label[0] = '\0';
  535. volid = 0;
  536. f_getlabel("", label, &volid);
  537. con_printf("sdcard: volume found, label \"%s\", volid %08x\n", label, volid);
  538. freeclust = 0;
  539. f_getfree("", &freeclust, &fs);
  540. con_printf("sdcard: %u/%u clusters free, clusters = %u bytes\n",
  541. freeclust, fs->n_fatent - 2, fs->csize << 9);
  542. return 0;
  543. }
  544. #define SYNC_TIME (1*TIMER_HZ) /* 1 s */
  545. /* Called from the main loop */
  546. void abcdisk_io_poll(void)
  547. {
  548. static uint32_t last_sync;
  549. static uint32_t last_timer = -1U;
  550. static uint32_t prev_abc_status = -1U;
  551. uint32_t now = timer_count();
  552. bool need_sync = false;
  553. uint32_t abc_status = ABC_STATUS & (ABC_STATUS_LIVE | ABC_STATUS_800);
  554. bool unmount_all = false;
  555. bool reset_all = false;
  556. if (now != last_timer) {
  557. /*
  558. * Periodically try to initialize the SD card if we are waiting
  559. * for it. The disk cache, however, will be initialized when fatfs
  560. * tries to mount the device.
  561. */
  562. if (sdc.status & STA_NOINIT) {
  563. if (!(sdcard_init() & STA_NOINIT))
  564. mount_disk();
  565. unmount_all = true;
  566. } else if (sdcard_present_poll() & STA_NOINIT) {
  567. unmount_all = true;
  568. } else {
  569. if ((now - last_sync) >= SYNC_TIME) {
  570. need_sync = true;
  571. last_sync = now;
  572. }
  573. }
  574. last_timer = now;
  575. }
  576. if (abc_status != prev_abc_status) {
  577. const char *host;
  578. prev_abc_status = abc_status;
  579. set_led(LED_ABCBUS, !!(abc_status & ABC_STATUS_LIVE));
  580. con_puts("ABC-bus host: ");
  581. con_puts(abc_status & ABC_STATUS_800 ? "ABC800" : "ABC80");
  582. con_puts(abc_status & ABC_STATUS_LIVE ? " (online)\n" : " (offline)\n");
  583. unmount_all = true;
  584. reset_all = true;
  585. }
  586. for (int i = 0; i < CONTROLLER_TYPES; i++) {
  587. struct ctl_state *state = &controllers[i];
  588. enum pending pending;
  589. if (unmount_all && state->initialized) {
  590. unmount_drives(state);
  591. state->initialized = false;
  592. } else if (!state->initialized && !(sdc.status & STA_NOINIT)) {
  593. init_drives(state);
  594. }
  595. if (reset_all)
  596. disk_reset_state(state);
  597. if (abc_status & ABC_STATUS_LIVE) {
  598. mask_irq(ABC_IRQ);
  599. pending = state->pending;
  600. state->pending = 0;
  601. unmask_irq(ABC_IRQ);
  602. if (pending & PEND_RESET)
  603. disk_reset_state(state);
  604. if (pending & PEND_IO)
  605. do_next_command(state);
  606. }
  607. if (state->initialized && need_sync)
  608. sync_drives(state);
  609. }
  610. if (need_sync) {
  611. /* Did we sync drives? */
  612. set_led(LED_DISKIO, false);
  613. }
  614. }
  615. /*
  616. * Called during initialization. Don't initialize the SD card here;
  617. * it will take too long and ABC will time out claiming no drives present.
  618. */
  619. void abcdisk_init(void)
  620. {
  621. static const struct abc_dev iodev_template = {
  622. .callback_mask = IDLE_CALLBACK_MASK,
  623. .status_first_out_mask = (uint8_t)~0x80,
  624. .status_first_inp_mask = (uint8_t)~0x80,
  625. .callback_out = abcdisk_callback_out,
  626. .callback_inp = abcdisk_callback_inp,
  627. .callback_cmd = abcdisk_callback_cmd
  628. };
  629. for (int i = 0; i < CONTROLLER_TYPES; i++) {
  630. struct ctl_state *state = &controllers[i];
  631. state->params = &parameters[i];
  632. state->iodev = iodev_template;
  633. abc_register(&state->iodev, state->params->devsel);
  634. disk_reset_state(state);
  635. }
  636. }