| 
														
															@@ -324,7 +324,9 @@ static void floppy_end_command(void *ack, unsigned int ack_len) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  */ 
														 | 
														
														 | 
														
															  */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															 static struct { 
														 | 
														
														 | 
														
															 static struct { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    unsigned int idx, nr_idx; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    unsigned int nr_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    unsigned int max_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    time_t deadline; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 } read; 
														 | 
														
														 | 
														
															 } read; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															 static void _write_28bit(uint32_t x) 
														 | 
														
														 | 
														
															 static void _write_28bit(uint32_t x) 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -342,7 +344,7 @@ static void rdata_encode_flux(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     timcnt_t prev = dma.prev_sample, curr, next; 
														 | 
														
														 | 
														
															     timcnt_t prev = dma.prev_sample, curr, next; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     uint32_t ticks; 
														 | 
														
														 | 
														
															     uint32_t ticks; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    ASSERT(read.idx < read.nr_idx); 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    ASSERT(read.nr_index < read.max_index); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															     /* We don't want to race the Index IRQ handler. */ 
														 | 
														
														 | 
														
															     /* We don't want to race the Index IRQ handler. */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     IRQ_global_disable(); 
														 | 
														
														 | 
														
															     IRQ_global_disable(); 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -350,10 +352,10 @@ static void rdata_encode_flux(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     /* Find out where the DMA engine's producer index has got to. */ 
														 | 
														
														 | 
														
															     /* Find out where the DMA engine's producer index has got to. */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     prod = ARRAY_SIZE(dma.buf) - dma_rdata.ndtr; 
														 | 
														
														 | 
														
															     prod = ARRAY_SIZE(dma.buf) - dma_rdata.ndtr; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    if (read.idx != index.count) { 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    if (read.nr_index != index.count) { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         /* We have just passed the index mark: Record information about  
														 | 
														
														 | 
														
															         /* We have just passed the index mark: Record information about  
														 | 
													
												
											
												
													
														| 
														 | 
														
															          * the just-completed revolution. */ 
														 | 
														
														 | 
														
															          * the just-completed revolution. */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        read.idx = index.count; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        read.nr_index = index.count; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         ticks = (timcnt_t)(index.rdata_cnt - prev); 
														 | 
														
														 | 
														
															         ticks = (timcnt_t)(index.rdata_cnt - prev); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         IRQ_global_enable(); /* we're done reading ISR variables */ 
														 | 
														
														 | 
														
															         IRQ_global_enable(); /* we're done reading ISR variables */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         u_buf[U_MASK(u_prod++)] = 0xff; 
														 | 
														
														 | 
														
															         u_buf[U_MASK(u_prod++)] = 0xff; 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -415,9 +417,6 @@ static void rdata_encode_flux(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															 static uint8_t floppy_read_prep(const struct gw_read_flux *rf) 
														 | 
														
														 | 
														
															 static uint8_t floppy_read_prep(const struct gw_read_flux *rf) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 { 
														 | 
														
														 | 
														
															 { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    if (rf->nr_idx == 0) 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        return ACK_BAD_COMMAND; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															- 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     /* Prepare Timer & DMA. */ 
														 | 
														
														 | 
														
															     /* Prepare Timer & DMA. */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     dma_rdata.mar = (uint32_t)(unsigned long)dma.buf; 
														 | 
														
														 | 
														
															     dma_rdata.mar = (uint32_t)(unsigned long)dma.buf; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     dma_rdata.ndtr = ARRAY_SIZE(dma.buf);     
														 | 
														
														 | 
														
															     dma_rdata.ndtr = ARRAY_SIZE(dma.buf);     
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -437,7 +436,9 @@ static uint8_t floppy_read_prep(const struct gw_read_flux *rf) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     flux_op.start = time_now(); 
														 | 
														
														 | 
														
															     flux_op.start = time_now(); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
														
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     memset(&read, 0, sizeof(read)); 
														 | 
														
														 | 
														
															     memset(&read, 0, sizeof(read)); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    read.nr_idx = rf->nr_idx; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    read.max_index = rf->max_index ?: INT_MAX; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    read.deadline = flux_op.start; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    read.deadline += rf->ticks ? time_from_samples(rf->ticks) : INT_MAX; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															     return ACK_OKAY; 
														 | 
														
														 | 
														
															     return ACK_OKAY; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 } 
														 | 
														
														 | 
														
															 } 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -476,9 +477,10 @@ static void floppy_read(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             floppy_state = ST_read_flux_drain; 
														 | 
														
														 | 
														
															             floppy_state = ST_read_flux_drain; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             u_cons = u_prod = avail = 0; 
														 | 
														
														 | 
														
															             u_cons = u_prod = avail = 0; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        } else if (read.idx >= read.nr_idx) { 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        } else if ((read.nr_index >= read.max_index) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+                   || (time_since(read.deadline) >= 0)) { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															-            /* Read all requested revolutions. */ 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+            /* Read all requested data. */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             floppy_flux_end(); 
														 | 
														
														 | 
														
															             floppy_flux_end(); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             floppy_state = ST_read_flux_drain; 
														 | 
														
														 | 
														
															             floppy_state = ST_read_flux_drain; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -523,6 +525,7 @@ static void floppy_read(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															 static struct { 
														 | 
														
														 | 
														
															 static struct { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     bool_t is_finished; 
														 | 
														
														 | 
														
															     bool_t is_finished; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    bool_t cue_at_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     bool_t terminate_at_index; 
														 | 
														
														 | 
														
															     bool_t terminate_at_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     uint32_t astable_period; 
														 | 
														
														 | 
														
															     uint32_t astable_period; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     uint32_t ticks; 
														 | 
														
														 | 
														
															     uint32_t ticks; 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -745,6 +748,7 @@ static uint8_t floppy_write_prep(const struct gw_write_flux *wf) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
														
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     memset(&write, 0, sizeof(write)); 
														 | 
														
														 | 
														
															     memset(&write, 0, sizeof(write)); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     write.flux_mode = FLUXMODE_idle; 
														 | 
														
														 | 
														
															     write.flux_mode = FLUXMODE_idle; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    write.cue_at_index = wf->cue_at_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     write.terminate_at_index = wf->terminate_at_index; 
														 | 
														
														 | 
														
															     write.terminate_at_index = wf->terminate_at_index; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															     return ACK_OKAY; 
														 | 
														
														 | 
														
															     return ACK_OKAY; 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -792,7 +796,7 @@ static void floppy_write_wait_data(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															 static void floppy_write_wait_index(void) 
														 | 
														
														 | 
														
															 static void floppy_write_wait_index(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 { 
														 | 
														
														 | 
														
															 { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    if (index.count == 0) { 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    if (write.cue_at_index && (index.count == 0)) { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         if (time_since(flux_op.start) > time_ms(2000)) { 
														 | 
														
														 | 
														
															         if (time_since(flux_op.start) > time_ms(2000)) { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             /* Timeout */ 
														 | 
														
														 | 
														
															             /* Timeout */ 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             floppy_flux_end(); 
														 | 
														
														 | 
														
															             floppy_flux_end(); 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -900,7 +904,7 @@ static uint8_t floppy_erase_prep(const struct gw_erase_flux *ef) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															     floppy_state = ST_erase_flux; 
														 | 
														
														 | 
														
															     floppy_state = ST_erase_flux; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
														
														 | 
														
															     flux_op.status = ACK_OKAY; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-    flux_op.end = time_now() + time_from_samples(ef->erase_ticks); 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+    flux_op.end = time_now() + time_from_samples(ef->ticks); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															  
														 | 
														
														 | 
														
															  
														 | 
													
												
											
												
													
														| 
														 | 
														
															     return ACK_OKAY; 
														 | 
														
														 | 
														
															     return ACK_OKAY; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 } 
														 | 
														
														 | 
														
															 } 
														 | 
													
												
											
										
											
												
													
														 | 
														
															@@ -1145,16 +1149,18 @@ static void process_command(void) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         goto out; 
														 | 
														
														 | 
														
															         goto out; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     } 
														 | 
														
														 | 
														
															     } 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     case CMD_READ_FLUX: { 
														 | 
														
														 | 
														
															     case CMD_READ_FLUX: { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        struct gw_read_flux rf = { .nr_idx = 2 }; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        if ((len < 2) || (len > (2 + sizeof(rf)))) 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        struct gw_read_flux rf; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        if (len != (2 + sizeof(rf))) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             goto bad_command; 
														 | 
														
														 | 
														
															             goto bad_command; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         memcpy(&rf, &u_buf[2], len-2); 
														 | 
														
														 | 
														
															         memcpy(&rf, &u_buf[2], len-2); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         u_buf[1] = floppy_read_prep(&rf); 
														 | 
														
														 | 
														
															         u_buf[1] = floppy_read_prep(&rf); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         goto out; 
														 | 
														
														 | 
														
															         goto out; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     } 
														 | 
														
														 | 
														
															     } 
														 | 
													
												
											
												
													
														| 
														 | 
														
															     case CMD_WRITE_FLUX: { 
														 | 
														
														 | 
														
															     case CMD_WRITE_FLUX: { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        struct gw_write_flux wf = { 0 }; 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															-        if ((len < 2) || (len > (2 + sizeof(wf)))) 
														 | 
														
														 | 
														
															 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        struct gw_write_flux wf = { 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+            .cue_at_index = 1, 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+            .terminate_at_index = 0 }; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															 
														 | 
														
														 | 
														
															+        if (len != (2 + sizeof(wf))) 
														 | 
													
												
											
												
													
														| 
														 | 
														
															             goto bad_command; 
														 | 
														
														 | 
														
															             goto bad_command; 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         memcpy(&wf, &u_buf[2], len-2); 
														 | 
														
														 | 
														
															         memcpy(&wf, &u_buf[2], len-2); 
														 | 
													
												
											
												
													
														| 
														 | 
														
															         u_buf[1] = floppy_write_prep(&wf); 
														 | 
														
														 | 
														
															         u_buf[1] = floppy_write_prep(&wf); 
														 |