11#![ allow( dead_code) ]
22
33use std:: borrow:: Cow ;
4+ use std:: collections:: VecDeque ;
45use std:: io:: { Cursor , Read } ;
56use std:: sync:: mpsc:: { self , Receiver , Sender } ;
67use std:: thread;
@@ -167,6 +168,7 @@ enum VMCommand {
167168 SetSingleStep ( bool ) ,
168169 SetBreakpoint ( Option < u32 > ) ,
169170 PrintVar ( U16String , Option < String > ) ,
171+ TxUART0 ( String ) ,
170172}
171173
172174struct VMState {
@@ -199,12 +201,47 @@ fn tui(
199201
200202 siv. add_fullscreen_layer (
201203 LinearLayout :: horizontal ( )
204+ . child (
205+ // slider to set the size of the UART0 panel
206+ PaddedView :: new (
207+ Margins :: tb ( 1 , 1 ) ,
208+ SliderView :: vertical ( 100 )
209+ . value ( stdout_scroll_height)
210+ . on_change ( |siv, value| {
211+ siv. call_on_name (
212+ "stdout_scroll" ,
213+ |v : & mut ResizedView < LinearLayout > | {
214+ v. set_height ( SizeConstraint :: Fixed ( value) ) ;
215+ } ,
216+ ) ;
217+ } ) ,
218+ )
219+ . fixed_width ( 1 ) ,
220+ )
202221 . child (
203222 LinearLayout :: vertical ( )
204223 . child (
205224 Panel :: new (
206- ScrollView :: new ( TextView :: new_with_content ( stdout) )
207- . scroll_strategy ( ScrollStrategy :: StickToBottom )
225+ LinearLayout :: vertical ( )
226+ . child (
227+ ScrollView :: new ( TextView :: new_with_content ( stdout) )
228+ . scroll_strategy ( ScrollStrategy :: StickToBottom )
229+ . full_height ( ) ,
230+ )
231+ . child (
232+ EditView :: new ( )
233+ . on_submit ( {
234+ let tx = tx. clone ( ) ;
235+ move |siv, cmd| {
236+ tx. send ( VMCommand :: TxUART0 ( cmd. to_string ( ) + "\r " ) )
237+ . unwrap ( ) ;
238+ siv. call_on_name ( "stdin" , |view : & mut EditView | {
239+ view. set_content ( "" ) ;
240+ } ) ;
241+ }
242+ } )
243+ . with_name ( "stdin" ) ,
244+ )
208245 . fixed_height ( stdout_scroll_height)
209246 . with_name ( "stdout_scroll" ) ,
210247 )
@@ -288,23 +325,6 @@ fn tui(
288325 ) ) ,
289326 ) ,
290327 )
291- . child (
292- // slider to set the size of the UART0 panel
293- PaddedView :: new (
294- Margins :: tb ( 1 , 1 ) ,
295- SliderView :: vertical ( 100 )
296- . value ( stdout_scroll_height)
297- . on_change ( |siv, value| {
298- siv. call_on_name (
299- "stdout_scroll" ,
300- |v : & mut ResizedView < ScrollView < TextView > > | {
301- v. set_height ( SizeConstraint :: Fixed ( value) ) ;
302- } ,
303- ) ;
304- } ) ,
305- )
306- . fixed_width ( 1 ) ,
307- )
308328 . full_screen ( ) ,
309329 ) ;
310330
@@ -545,7 +565,8 @@ fn main() -> Result<(), Box<dyn Error>> {
545565 let mut prev_power = true ;
546566 let mut frozen = false ;
547567 let mut ticks = 0 ;
548- let mut uart_buf = String :: new ( ) ;
568+ let mut uart_rx_buf = String :: new ( ) ;
569+ let mut uart_tx_buf = VecDeque :: < u8 > :: new ( ) ;
549570 let state_update_interval = Duration :: from_secs_f64 ( 1. / 8. ) ;
550571 let start = Instant :: now ( ) ;
551572 let mut run_start = start;
@@ -557,24 +578,38 @@ fn main() -> Result<(), Box<dyn Error>> {
557578 ticks += 1 ;
558579 }
559580
560- // UART0 terminal
581+ // UART0 rx
561582 if let BuildingData :: Memory ( uart0) = & mut * uart0. data . borrow_mut ( ) {
562583 let mut rx_read = ( uart0[ UART_RX_READ ] as usize ) % uart_fifo_modulo;
563584 let rx_write = ( uart0[ UART_RX_WRITE ] as usize ) % uart_fifo_modulo;
564585 if rx_read != rx_write {
565586 while rx_read != rx_write {
566587 let c = uart0[ UART_RX_START + rx_read] as u8 ;
567- uart_buf . push ( c as char ) ;
588+ uart_rx_buf . push ( c as char ) ;
568589 rx_read = ( rx_read + 1 ) % uart_fifo_modulo;
569590 }
570591 uart0[ UART_RX_READ ] = rx_write as f64 ;
571592
572593 if do_tui {
573- stdout. append ( & uart_buf ) ;
594+ stdout. append ( & uart_rx_buf ) ;
574595 } else {
575- print ! ( "{uart_buf }" ) ;
596+ print ! ( "{uart_rx_buf }" ) ;
576597 }
577- uart_buf. clear ( ) ;
598+ uart_rx_buf. clear ( ) ;
599+ }
600+
601+ if !uart_tx_buf. is_empty ( ) {
602+ let tx_read = ( uart0[ UART_TX_READ ] as usize ) % uart_fifo_modulo;
603+ let mut tx_write = ( uart0[ UART_TX_WRITE ] as usize ) % uart_fifo_modulo;
604+ let mut next_tx_write = ( tx_write + 1 ) % uart_fifo_modulo;
605+ while next_tx_write != tx_read
606+ && let Some ( c) = uart_tx_buf. pop_front ( )
607+ {
608+ uart0[ tx_write] = c as f64 ;
609+ tx_write = next_tx_write;
610+ next_tx_write = ( tx_write + 1 ) % uart_fifo_modulo;
611+ }
612+ uart0[ UART_TX_WRITE ] = tx_write as f64 ;
578613 }
579614 }
580615
@@ -673,6 +708,9 @@ fn main() -> Result<(), Box<dyn Error>> {
673708 }
674709 } ;
675710 }
711+ VMCommand :: TxUART0 ( msg) => {
712+ uart_tx_buf. extend ( msg. as_bytes ( ) ) ;
713+ }
676714 }
677715 }
678716
0 commit comments