1
2
3
4
5
6
7
8
9
10
11
12
13 tty_interrupt:
14 proc (a_wtcbp, a_type, a_info);
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64 dcl a_wtcbp ptr;
65 dcl a_type fixed bin;
66 dcl a_info bit (72) aligned;
67
68
69
70
71 dcl i fixed bin;
72 dcl int_type fixed bin;
73 dcl devx fixed bin;
74 dcl charx fixed bin;
75 dcl echbufp ptr;
76 dcl this_char char (1) unaligned;
77 dcl echo_tally fixed bin (9);
78 dcl sync_ctr_tally fixed bin;
79 dcl inchain fixed bin (18);
80 dcl code fixed bin (35);
81 dcl next_offset fixed bin;
82 dcl last_offset fixed bin;
83 dcl new_headp ptr;
84 dcl old_tailp ptr;
85 dcl new_first_tally fixed bin;
86 dcl old_last_tally fixed bin;
87 dcl max_tally fixed bin;
88 dcl filled bit (1);
89 dcl source_ptr ptr;
90 dcl target_ptr ptr;
91 dcl start_time fixed bin (71);
92 dcl echnego_from_mux_flag bit (1);
93 dcl echnego_scan_start fixed bin;
94 dcl r0_did_echo bit (1);
95 dcl uncp_flag bit (1);
96 dcl 1 echo_start_data,
97 2 ctr fixed bin (35),
98 2 screenleft fixed bin (35);
99
100
101
102 dcl new_chars char (new_first_tally) based;
103
104
105
106
107 dcl (addr, bin, clock, divide, hbound, max, min, null,
108 ptr, unspec, rank, rel, size, string, substr) builtin;
109
110
111
112
113 dcl meter_response_time entry (bit (36) aligned, fixed bin);
114 dcl pxss$ring_0_wakeup entry (bit (36) aligned, fixed bin (71), fixed bin (71), fixed bin (35));
115 dcl pxss$unique_ring_0_wakeup entry (bit (36) aligned, fixed bin (71), fixed bin (71), fixed bin (35));
116 dcl pxss$ips_wakeup_int entry (bit (36) aligned, bit (35) aligned);
117 dcl syserr entry options (variable);
118
119
120
121
122 dcl error_table_$noalloc fixed bin (35) ext static;
123 dcl error_table_$invalid_write fixed bin (35) ext static;
124 dcl sys_info$quit_mask bit (35) aligned ext static;
125
126
127
128 dcl CRASH_SYSTEM fixed bin int static options (constant) init (1);
129
130 dcl line_delimiter_octal (16) bit (9) int static options (constant)
131 init ("012"b3, (2) (1)"055"b3, "012"b3, (3) (1)"003"b3, (5) (1)"012"b3, (3) (1)"003"b3, "012"b3);
132 dcl line_delimiter (16) char (1) based (addr (line_delimiter_octal));
133
134 dcl no_write_code fixed bin (35) internal static;
135 dcl noalloc_code fixed bin (35) internal static;
136 ^L
137 %include wtcb;
138 %include mcs_interrupt_info;
139 %include tty_buf;
140 %include tty_buffer_block;
141 %include net_event_message;
142 %include tty_space_man_dcls;
143 %include channel_manager_dcls;
144 %include line_types;
145 %include mcs_echo_neg_sys;
146 %include lct;
147 %include set_wakeup_table_info;
148 %include response_transitions;
149 %include multiplexer_types;
150 ^L
151 interrupt:
152 entry;
153
154 wtcbp = a_wtcbp;
155 int_type = a_type;
156 interrupt_info = a_info;
157 devx = wtcb.devx;
158 ttybp = addr (tty_buf$);
159
160 uncp_flag = is_parent_mpx (UNCP_MPX);
161
162 if int_type = DIALUP
163 then do;
164 unspec (dialup_info) = interrupt_info;
165 if wtcb.dialing
166 then do;
167 wtcb.dial_status_valid = "1"b;
168 wtcb.dial_status_code = 0;
169 end;
170
171
172 wtcb.line_type = dialup_info.line_type;
173 wtcb.baud_rate = dialup_info.baud_rate;
174 wtcb.max_buf_size = dialup_info.max_buf_size;
175 wtcb.buffer_pad = dialup_info.buffer_pad;
176 wtcb.line_delimiter = line_delimiter (wtcb.line_type);
177 wtcb.receive_mode_device = dialup_info.receive_mode_device;
178
179 if uncp_flag then wtcb.send_turn = "0"b;
180
181 do i = 1 to n_sync_line_types while (sync_line_type (i) ^= wtcb.line_type);
182 end;
183 wtcb.sync_line = (i <= n_sync_line_types);
184
185 wtcb.flags.dialed = "1"b;
186 wtcb.uproc = wtcb.hproc;
187
188 unspec (net_event_message) = "0"b;
189 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
190 net_event_message.network_type = MCS_NETWORK_TYPE;
191 net_event_message.handle = devx;
192 net_event_message.type = MCS_DIALUP_MSG;
193 call pxss$ring_0_wakeup (wtcb.hproc, wtcb.hevent, net_event_message_arg, 0);
194
195 end;
196
197 else if int_type = HANGUP
198 then do;
199 unspec (net_event_message) = "0"b;
200 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
201 net_event_message.network_type = MCS_NETWORK_TYPE;
202 net_event_message.handle = devx;
203 net_event_message.type = MCS_HANGUP_MSG;
204 call pxss$ring_0_wakeup (wtcb.hproc, wtcb.hevent, net_event_message_arg, (0));
205
206
207 call kill_line;
208 end;
209
210 else if int_type = CRASH
211 then call kill_line;
212
213 else if int_type = SEND_OUTPUT
214 then do;
215 wtcb.send_output = "1"b;
216 if wtcb.write_first ^= 0
217 then call send_next_page;
218 else if wtcb.negotiating_echo
219 then do;
220
221 echo_datap = ptr (ttybp, wtcb.echdp);
222 if echo_data.echo_start_pending_sndopt
223 then call start_negotiated_echo;
224
225 end;
226
227 if wtcb.write_first = 0
228 then if wtcb.wflag
229 then do;
230 unspec (net_event_message) = "0"b;
231 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
232 net_event_message.network_type = MCS_NETWORK_TYPE;
233 net_event_message.handle = devx;
234 net_event_message.type = MCS_WRITE_MSG;
235 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
236 wtcb.wflag = "0"b;
237 end;
238 end;
239
240 else if int_type = INPUT_AVAILABLE
241 then do;
242 wtcb.input_available = "1"b;
243 if wtcb.rflag
244 then do;
245 unspec (net_event_message) = "0"b;
246 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
247 net_event_message.network_type = MCS_NETWORK_TYPE;
248 net_event_message.handle = devx;
249 net_event_message.type = MCS_READ_MSG;
250 call meter_response_time (wtcb.uproc, TTY_WAKEUP);
251 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
252 wtcb.rflag = "0"b;
253 end;
254 end;
255
256 else if int_type = ACCEPT_INPUT
257 then do;
258 unspec (rtx_info) = interrupt_info;
259 if rtx_info.formfeed_present
260 then do;
261 if ^rtx_info.output_in_ring_0 & wtcb.write_first = 0
262
263 then wtcb.actline = 0;
264 end;
265
266 inchain = bin (rtx_info.chain_head);
267 if inchain = 0
268 then return;
269
270 sync_ctr_tally = 0;
271 r0_did_echo = "0"b;
272
273 last_offset = bin (rtx_info.chain_tail);
274 ^L
275 if wtcb.negotiating_echo
276 then do;
277 start_time = clock ();
278 tty_buf.echo_neg_interrupts = tty_buf.echo_neg_interrupts + 1;
279
280 echo_datap = ptr (ttybp, wtcb.echdp);
281 echbufp = null ();
282 echnego_from_mux_flag = "0"b;
283 if wtcb.write_last = 0
284 then old_tailp = null;
285 else do;
286 old_tailp = ptr (ttybp, wtcb.write_last);
287 old_last_tally = old_tailp -> buffer.tally;
288 if old_last_tally ^< max_buffer_tally (old_tailp -> buffer.size_code) - wtcb.buffer_pad
289 then old_tailp = null;
290 end;
291
292
293 do blockp = ptr (ttybp, rtx_info.chain_head) repeat (ptr (ttybp, buffer.next)) while (rel (blockp));
294
295 echnego_scan_start = 0;
296
297 if echo_data.mux_will_echnego
298 & buffer.next = 0
299 & ^rtx_info.break_char
300
301 & buffer.tally > 0
302 then do;
303
304
305
306
307
308
309 do echnego_scan_start = max (0, buffer.tally - 4) to buffer.tally - 1
310 while (echoable (buffer.chars (echnego_scan_start)));
311 end;
312 if echnego_scan_start > echo_data.horiz_room_left
313
314 then echnego_scan_start = echo_data.horiz_room_left;
315
316 echo_data.horiz_room_left = echo_data.horiz_room_left - echnego_scan_start;
317 echo_data.chars_echoed = echo_data.chars_echoed + echnego_scan_start;
318 sync_ctr_tally = sync_ctr_tally - echnego_scan_start;
319
320 tty_buf.echo_neg_mux_chars = tty_buf.echo_neg_mux_chars + echnego_scan_start;
321
322 rtx_info.break_char = "1"b;
323 echnego_from_mux_flag = "1"b;
324 if echo_data.horiz_room_left ^> 0
325 then go to negotiated_echo_ceases;
326 end;
327
328
329
330 do charx = echnego_scan_start to buffer.tally - 1;
331
332 this_char = buffer.chars (charx);
333 if ^echoable (this_char)
334 then go to negotiated_echo_ceases;
335
336
337
338
339 if echo_data.horiz_room_left ^> 0
340 then go to negotiated_echo_ceases;
341 if echnego_from_mux_flag
342 then do;
343 echo_data.chars_echoed = echo_data.chars_echoed + 1;
344 tty_buf.echo_neg_mux_chars = tty_buf.echo_neg_mux_chars + 1;
345
346 sync_ctr_tally = sync_ctr_tally - 1;
347 end;
348 else if old_tailp ^= null
349 then do;
350 r0_did_echo = "1"b;
351 old_tailp -> buffer.chars (old_last_tally) = this_char;
352 echo_data.chars_echoed = echo_data.chars_echoed + 1;
353 tty_buf.echo_neg_r0_chars = tty_buf.echo_neg_r0_chars + 1;
354 old_last_tally, old_tailp -> buffer.tally = old_last_tally + 1;
355 if old_last_tally ^< max_buffer_tally (old_tailp -> buffer.size_code) - wtcb.buffer_pad
356 then old_tailp = null;
357 end;
358 else do;
359
360 if echbufp = null
361 then do;
362
363 r0_did_echo = "1"b;
364 lctp = tty_buf.lct_ptr;
365
366 lctep = addr (lct.lcte_array (devx));
367 lctep = addr (lct.lcte_array (lcte.physical_channel_devx));
368 if lcte.output_words >= divide (tty_buf.bleft, output_bpart, 17, 0)
369
370 then go to negotiated_echo_ceases;
371
372
373 call tty_space_man$get_buffer (devx, 16, OUTPUT, echbufp);
374 if echbufp = null
375 then go to negotiated_echo_ceases;
376
377 echo_tally = 0;
378 end;
379 echbufp -> buffer.chars (echo_tally) = this_char;
380
381 echo_tally = echo_tally + 1;
382
383
384 if echo_tally >= max_buffer_tally (echbufp -> buffer.size_code) - wtcb.buffer_pad
385 then call ship_echo_buffer;
386 end;
387 echo_data.horiz_room_left = echo_data.horiz_room_left - 1;
388 end;
389 end;
390 rtx_info.break_char = "0"b;
391 go to negotiated_echo_continues;
392
393
394 negotiated_echo_ceases:
395 echo_data.echo_start_pending_sndopt = "0"b;
396
397 wtcb.negotiating_echo = "0"b;
398 negotiated_echo_continues:
399 if echbufp ^= null
400 then call ship_echo_buffer;
401 tty_buf.echo_neg_time = tty_buf.echo_neg_time + clock () - start_time;
402 end;
403
404 if wtcb.echdp ^= "000000"b3
405 then do;
406 echo_datap = ptr (ttybp, wtcb.echdp);
407 if echo_data.synchronized
408 then do;
409 if sync_ctr_tally < 0
410 then echo_data.sync_ctr = 0;
411 do blockp = ptr (ttybp, rtx_info.chain_head) repeat (ptr (ttybp, buffer.next))
412 while (rel (blockp));
413
414 sync_ctr_tally = sync_ctr_tally + buffer.tally;
415 end;
416 echo_data.sync_ctr = echo_data.sync_ctr + sync_ctr_tally;
417 if r0_did_echo & wtcb.write_first = 0
418 then do;
419
420 tty_buf.echo_neg_mux_nonecho = tty_buf.echo_neg_mux_nonecho + 1;
421 if wtcb.negotiating_echo
422 then call start_negotiated_echo;
423
424 end;
425 end;
426 end;
427
428 if uncp_flag then
429 if wtcb.receive_mode_device
430 then wtcb.wake_tbl = "0"b;
431
432 if wtcb.wake_tbl & ^wtcb.allow_wakeup
433 then call scan_iw_char;
434
435 if wtcb.mark_set
436 then do;
437 blockp = ptr (ttybp, inchain);
438 buffer.mark = "1"b;
439 wtcb.mark_set = "0"b;
440 end;
441
442 if wtcb.fblock = 0
443 then do;
444 wtcb.fblock = inchain;
445 wtcb.fchar = 0;
446 end;
447 else do;
448 old_tailp = ptr (ttybp, wtcb.lblock);
449 next_offset = bin (rtx_info.chain_head);
450 if ^old_tailp -> buffer.converted
451 then do;
452 old_last_tally = old_tailp -> buffer.tally;
453
454 max_tally = max_buffer_tally (old_tailp -> buffer.size_code);
455
456 filled = "0"b;
457 do while ((next_offset ^= 0) & ^filled);
458
459 new_headp = ptr (ttybp, next_offset);
460 new_first_tally = new_headp -> buffer.tally;
461
462 if (old_last_tally + new_first_tally <= max_tally) & ^new_headp -> buffer.mark
463
464 then do;
465 source_ptr = addr (new_headp -> buffer.chars (0));
466 target_ptr = addr (old_tailp -> buffer.chars (old_last_tally));
467 target_ptr -> new_chars = source_ptr -> new_chars;
468 old_last_tally = old_last_tally + new_first_tally;
469 next_offset = new_headp -> buffer.next;
470
471 call tty_space_man$free_buffer (devx, INPUT, new_headp);
472
473 end;
474
475 else filled = "1"b;
476 end;
477
478 old_tailp -> buffer.tally = old_last_tally;
479 end;
480 old_tailp -> buffer.next = next_offset;
481 if next_offset = 0
482 then last_offset = 0;
483
484 end;
485
486 if last_offset ^= 0
487 then wtcb.lblock = last_offset;
488
489 if wtcb.wake_tbl & ^wtcb.allow_wakeup
490 then call check_iw_limit;
491
492 if rtx_info.break_char & ^rtx_info.output_in_ring_0
493
494 then do;
495 if ^rtx_info.output_in_fnp
496 then wtcb.actcol, wtcb.white_col = 0;
497
498 if wtcb.flags.count_lines & ^wtcb.breakall
499
500 then wtcb.actline = wtcb.actline + 1;
501 end;
502 if (rtx_info.break_char | wtcb.wru)
503 & wtcb.rflag
504 then do;
505 if wtcb.wake_tbl & ^wtcb.allow_wakeup
506 then if wtcb.prompt_len > 0
507 then call send_prompt;
508 else ;
509 else do;
510 unspec (net_event_message) = "0"b;
511 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
512 net_event_message.network_type = MCS_NETWORK_TYPE;
513 net_event_message.handle = devx;
514 net_event_message.type = MCS_READ_MSG;
515 call meter_response_time (wtcb.uproc, TTY_WAKEUP);
516 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, 0);
517
518 wtcb.rflag = "0"b;
519 end;
520 end;
521 end;
522
523 else if int_type = INPUT_REJECTED
524 then do;
525 if wtcb.fblock ^= 0
526 then do;
527 unspec (net_event_message) = "0"b;
528 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
529 net_event_message.network_type = MCS_NETWORK_TYPE;
530 net_event_message.handle = devx;
531 net_event_message.type = MCS_READ_MSG;
532 if wtcb.rflag
533 then do;
534 call meter_response_time (wtcb.uproc, TTY_WAKEUP);
535 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
536 wtcb.rflag = "0"b;
537 end;
538
539 else call pxss$unique_ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
540 end;
541 end;
542
543 else if int_type = QUIT
544 then do;
545 if wtcb.flags.hndlquit
546 then do;
547 if wtcb.negotiating_echo
548 then do;
549 echo_datap = ptr (ttybp, wtcb.echdp);
550 echo_data.echo_start_pending_sndopt, echo_data.synchronized, wtcb.negotiating_echo = "0"b;
551 end;
552 if wtcb.fblock ^= 0
553 then do;
554 call tty_space_man$free_chain (devx, INPUT, ptr (ttybp, wtcb.fblock));
555 wtcb.fblock, wtcb.lblock = 0;
556 end;
557
558 if wtcb.write_first ^= 0
559 then do;
560 call tty_space_man$free_chain (devx, OUTPUT, ptr (ttybp, wtcb.write_first));
561 wtcb.write_first, wtcb.write_last, wtcb.write_cnt = 0;
562 end;
563
564 wtcb.white_col = 0;
565 wtcb.actcol = 0;
566 end;
567
568 unspec (net_event_message) = "0"b;
569 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
570 net_event_message.network_type = MCS_NETWORK_TYPE;
571 net_event_message.handle = devx;
572
573 if wtcb.wflag | wtcb.rflag
574 then do;
575 if wtcb.wflag
576 then net_event_message.type = MCS_WRITE_MSG;
577
578 else net_event_message.type = MCS_READ_MSG;
579 call meter_response_time (wtcb.uproc, TTY_WAKEUP);
580 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, 0);
581
582 wtcb.wflag, wtcb.rflag = "0"b;
583 end;
584
585 if wtcb.flags.qenable
586 then do;
587 net_event_message.type = MCS_QUIT_MSG;
588 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, 0);
589
590 call pxss$ips_wakeup_int (wtcb.uproc, sys_info$quit_mask);
591
592 wtcb.flags.qflag = "1"b;
593 wtcb.mark_set = "0"b;
594 end;
595
596 if wtcb.count_lines
597 then if wtcb.flags.scroll
598 then wtcb.actline = 0;
599 else wtcb.actline = wtcb.actline + 1;
600
601 wtcb.end_frame = "0"b;
602
603 tty_buf.nquits = tty_buf.nquits + 1;
604
605 end;
606
607 else if int_type = LINE_STATUS
608 then do;
609 if ^wtcb.line_status_disabled
610 then if wtcb.uproc ^= "0"b
611 then do;
612 wtcb.line_status = interrupt_info;
613 wtcb.line_status_present = "1"b;
614 unspec (net_event_message) = "0"b;
615 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
616 net_event_message.network_type = MCS_NETWORK_TYPE;
617 net_event_message.handle = devx;
618 net_event_message.type = MCS_LINE_STATUS_MSG;
619 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, 0);
620 end;
621
622 return;
623
624 end;
625
626 else if int_type = DIAL_STATUS
627 then do;
628 if wtcb.dialing
629 then do;
630 wtcb.dial_status_valid = "1"b;
631 wtcb.dial_status_code = bin (substr (interrupt_info, 1, 8), 8);
632 unspec (net_event_message) = "0"b;
633 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
634 net_event_message.network_type = MCS_NETWORK_TYPE;
635 net_event_message.handle = devx;
636 net_event_message.type = MCS_DIALOUT_MSG;
637 call pxss$ring_0_wakeup (wtcb.hproc, wtcb.hevent, net_event_message_arg, 0);
638
639
640 end;
641 end;
642
643 else if int_type = WRU_TIMEOUT
644 then do;
645 if wtcb.flags.dialed
646 then do;
647 wtcb.rflag = "0"b;
648 unspec (net_event_message) = "0"b;
649 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
650 net_event_message.network_type = MCS_NETWORK_TYPE;
651 net_event_message.handle = devx;
652 net_event_message.type = MCS_READ_MSG;
653 call pxss$ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, 0);
654
655 end;
656 end;
657
658 else if int_type = SPACE_AVAILABLE
659 then if wtcb.write_first ^= 0
660 then call send_next_page;
661 else do;
662 unspec (net_event_message) = "0"b;
663 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
664 net_event_message.network_type = MCS_NETWORK_TYPE;
665 net_event_message.handle = devx;
666 net_event_message.type = MCS_UNSPECIFIED_MSG;
667 call pxss$unique_ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
668 end;
669
670 else if int_type = ACKNOWLEDGE_ECHNEGO_INIT
671 then do;
672 echo_datap = ptr (ttybp, wtcb.echdp);
673 if echo_datap ^= ttybp
674 then do;
675 echo_data.awaiting_start_sync = "0"b;
676 echo_data.synchronized = "1"b;
677 echo_data.sync_ctr = 0;
678 end;
679 end;
680 else if int_type = ACKNOWLEDGE_ECHNEGO_STOP
681 then do;
682 echo_datap = ptr (ttybp, wtcb.echdp);
683 wtcb.negotiating_echo = "0"b;
684 if echo_datap ^= ttybp
685 then do;
686 echo_data.awaiting_stop_sync = "0"b;
687 echo_data.echo_start_pending_sndopt = "0"b;
688 unspec (net_event_message) = "0"b;
689 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
690 net_event_message.network_type = MCS_NETWORK_TYPE;
691 net_event_message.handle = devx;
692 net_event_message.type = MCS_UNSPECIFIED_MSG;
693 call pxss$unique_ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
694 end;
695 end;
696
697 else if int_type = MASKED
698 then do;
699 unspec (net_event_message) = "0"b;
700 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
701 net_event_message.network_type = MCS_NETWORK_TYPE;
702 net_event_message.handle = devx;
703 net_event_message.type = MCS_MASKED_MSG;
704 call pxss$ring_0_wakeup (wtcb.hproc, wtcb.hevent, net_event_message_arg, 0);
705 call kill_line;
706 wtcb.masked = "1"b;
707 end;
708
709 else
710 bad_int:
711 call syserr (CRASH_SYSTEM, "tty_interrupt: unrecognized interrupt type (^d) for devx ^d", int_type, devx);
712
713 return;
714 ^L
715
716
717 send_next_page:
718 proc;
719
720 dcl headp ptr;
721 dcl next_head fixed bin;
722
723 if wtcb.send_output
724 then do;
725 headp, blockp = ptr (ttybp, wtcb.write_first);
726
727 do while (^buffer.end_of_page & buffer.next ^= 0);
728
729 if buffer.mark
730 then wtcb.mark_set = "1"b;
731 blockp = ptr (ttybp, buffer.next);
732 end;
733
734 if buffer.mark
735 then wtcb.mark_set = "1"b;
736 next_head = buffer.next;
737 buffer.next = 0;
738 wtcb.end_frame = buffer.end_of_page;
739
740 call channel_manager$write (devx, headp, code);
741 if code = noalloc_code
742 then do;
743 call tty_space_man$needs_space (devx);
744 code = 0;
745 end;
746
747
748 if headp ^= null
749 then do;
750 if code = 0
751 then do;
752 blockp = headp;
753 do while (buffer.next ^= 0);
754 if buffer.mark
755 then wtcb.mark_set = "0"b;
756 blockp = ptr (ttybp, buffer.next);
757 end;
758
759 if buffer.mark
760 then wtcb.mark_set = "0"b;
761 buffer.next = next_head;
762 if next_head = 0
763 then wtcb.write_last = bin (rel (blockp));
764
765 next_head = bin (rel (headp));
766 end;
767
768 else do;
769 call tty_space_man$free_chain (devx, OUTPUT, headp);
770
771 wtcb.mark_set = "0"b;
772 wtcb.error_code = code;
773 unspec (net_event_message) = "0"b;
774 net_event_message.version = NET_EVENT_MESSAGE_VERSION_1;
775 net_event_message.network_type = MCS_NETWORK_TYPE;
776 net_event_message.handle = devx;
777 net_event_message.type = MCS_UNSPECIFIED_MSG;
778
779 call pxss$unique_ring_0_wakeup (wtcb.uproc, wtcb.event, net_event_message_arg, (0));
780 end;
781 end;
782
783 wtcb.write_first = next_head;
784 if wtcb.write_first = 0
785 then wtcb.write_last = 0;
786 else if code ^= 0
787 then do;
788 call tty_space_man$free_chain (devx, OUTPUT, ptr (ttybp, wtcb.write_first));
789 wtcb.write_first, wtcb.write_last = 0;
790 end;
791 wtcb.send_output = "0"b;
792 end;
793
794 return;
795 end ;
796 ^L
797
798
799 kill_line:
800 proc;
801
802 dcl sync_flag bit (1);
803 dcl masked_flag bit (1);
804
805 if wtcb.fblock ^= 0
806 then call tty_space_man$free_chain (devx, INPUT, ptr (ttybp, wtcb.fblock));
807
808 if wtcb.write_first ^= 0
809 then call tty_space_man$free_chain (devx, OUTPUT, ptr (ttybp, wtcb.write_first));
810
811
812
813 masked_flag = wtcb.flags.masked;
814 sync_flag = wtcb.flags.sync_line;
815 string (wtcb.flags) = ""b;
816 string (wtcb.more_flags) = ""b;
817 wtcb.flags.masked = masked_flag;
818 wtcb.flags.sync_line = sync_flag;
819
820 wtcb.uproc = ""b;
821 wtcb.white_col, wtcb.fblock, wtcb.lblock = 0;
822 wtcb.fchar, wtcb.actline, wtcb.actcol, wtcb.nramsgs = 0;
823 wtcb.write_first, wtcb.write_last = 0;
824 wtcb.prompt_len = 0;
825 wtcb.error_code = 0;
826
827 if wtcb.echdp ^= ""b
828 then do;
829 call tty_space_man$free_space (size (echo_data), ptr (ttybp, wtcb.echdp));
830 wtcb.echdp = ""b;
831 end;
832 if wtcb.waketp ^= ""b
833 then do;
834 call tty_space_man$free_space (size (wakeup_table), ptr (ttybp, wtcb.waketp));
835 wtcb.waketp = ""b;
836 end;
837
838 end ;
839 ^L
840 echoable:
841 procedure (test_char) returns (bit (1) aligned);
842
843
844
845 dcl test_char char (1);
846 dcl char_pos fixed bin (9);
847
848 char_pos = rank (test_char);
849 if char_pos > hbound (echo_data.break, 1)
850 then return ("0"b);
851
852
853
854 else return (^echo_data.break (char_pos));
855 end echoable;
856 ^L
857 ship_echo_buffer:
858 proc;
859
860
861
862 dcl loc_echbufp ptr;
863 dcl loc_lastp ptr;
864
865 echbufp -> buffer.tally = echo_tally;
866 loc_echbufp = echbufp;
867 code = 0;
868
869 if wtcb.write_first ^= 0
870 then do;
871 loc_lastp = ptr (ttybp, wtcb.write_last);
872 wtcb.write_last,
873 loc_lastp -> buffer.next = bin (rel (loc_echbufp));
874 loc_echbufp = null;
875 end;
876
877 else if ^wtcb.send_output
878 then do;
879 wtcb.write_first, wtcb.write_last = bin (rel (loc_echbufp));
880 loc_echbufp = null;
881 end;
882
883 else do;
884 wtcb.send_output = "0"b;
885 call channel_manager$write (devx, loc_echbufp, code);
886 end;
887
888 if loc_echbufp = null & code = 0
889 then do;
890 echo_data.chars_echoed = echo_data.chars_echoed + echo_tally;
891 tty_buf.echo_neg_r0_chars = tty_buf.echo_neg_r0_chars + echo_tally;
892
893 end;
894 else do;
895 code = 1;
896 call tty_space_man$free_buffer (devx, OUTPUT, echbufp);
897 end;
898 echbufp = null;
899 if code ^= 0
900 then go to negotiated_echo_ceases;
901
902 end ship_echo_buffer;
903 ^L
904
905
906 scan_iw_char:
907 proc;
908
909 dcl charx fixed bin;
910 dcl i fixed bin;
911
912 wakeup_tablep = ptr (ttybp, wtcb.waketp);
913 do blockp = ptr (ttybp, rtx_info.chain_head) repeat (ptr (ttybp, buffer.next)) while (rel (blockp));
914 do charx = 0 to buffer.tally - 1;
915 i = bin (unspec (buffer.chars (charx)));
916 if i <= 127
917 then if wakeup_table.wake_map (i)
918 then do;
919 wtcb.allow_wakeup = "1"b;
920 return;
921 end;
922 end;
923 end;
924
925 end;
926
927
928
929
930
931 check_iw_limit:
932 proc;
933
934 lctp = tty_buf.lct_ptr;
935 lctep = addr (lct.lcte_array (devx));
936 lctep = addr (lct.lcte_array (lcte.physical_channel_devx));
937 if lcte.input_words > min (128, divide (tty_buf.bleft, 4, 17, 0))
938 then wtcb.allow_wakeup = "1"b;
939
940 end;
941 ^L
942
943
944 send_prompt:
945 proc;
946
947 dcl bufp ptr;
948
949
950 call tty_space_man$get_buffer (devx, 16, OUTPUT, bufp);
951 if bufp = null
952 then return;
953
954 substr (string (bufp -> buffer.chars), 1, wtcb.prompt_len) = substr (wtcb.prompt, 1, wtcb.prompt_len);
955 bufp -> buffer.tally = wtcb.prompt_len;
956 if wtcb.write_first = 0
957 then wtcb.write_first = bin (rel (bufp));
958 else ptr (ttybp, wtcb.write_last) -> buffer.next = bin (rel (bufp));
959 wtcb.write_last = bin (rel (bufp));
960
961 call send_next_page;
962
963 end;
964 ^L
965 set_static:
966 entry;
967
968
969
970 noalloc_code = error_table_$noalloc;
971 no_write_code = error_table_$invalid_write;
972 return;
973 ^L
974 start_negotiated_echo:
975 proc;
976 echo_start_data.ctr = echo_data.sync_ctr;
977 echo_start_data.screenleft = echo_data.horiz_room_left;
978 call channel_manager$control (devx, "start_negotiated_echo", addr (echo_start_data), code);
979 if code = 0
980 then echo_data.echo_start_pending_sndopt = "0"b;
981 else if code = no_write_code
982 then echo_data.echo_start_pending_sndopt = "1"b;
983 tty_buf.echo_neg_sndopt_restarts = tty_buf.echo_neg_sndopt_restarts + 1;
984
985 end;
986 ^L
987 is_parent_mpx:
988 proc (parent_mpx_type) returns (bit (1));
989
990 dcl parent_mpx_type fixed bin;
991 dcl temp_lctep ptr;
992
993 lctp = tty_buf.lct_ptr;
994 lctep = addr (lct.lcte_array (devx));
995 if lcte.major_channel_devx ^= 0 then do;
996 temp_lctep = addr (lct.lcte_array (lcte.major_channel_devx));
997 if temp_lctep->lcte.channel_type = parent_mpx_type then return ("1"b);
998 end;
999 else if lcte.channel_type = parent_mpx_type then return ("1"b);
1000 return ("0"b);
1001 end is_parent_mpx;
1002
1003 ^L
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022 end ;