[net.unix] Transmitting BREAK

RMark.MINITAB%denver@sri-unix.UUCP (02/12/84)

How can a BREAK be transmitted via /dev/tty01 from the shell or a C
program?

gwyn%brl-vld@sri-unix.UUCP (02/13/84)

From:      Doug Gwyn (VLD/VMB) <gwyn@brl-vld>

/*	sendbreak -- send BREAK to terminal	*/

#include	<fcntl.h>
#include	<sys/ioctl.h>

extern void	exit(), perror();
extern int	ioctl(), open();

main( argc, argv )
	int	argc;
	char	*argv[];
	{
	register char	*tty;		/* terminal file name */
	register int	fd;		/* terminal file descriptor */

	if ( argc < 2 )
		tty = "/dev/tty";
	else
		tty = argv[1];

	if ( (fd = open( tty, O_RDONLY )) < 0
	  || ioctl( fd, TCSBRK, 0 ) < 0
	   )	{
		perror( tty );
		exit( 1 );
		}

	exit( 0 );
	}

RMark.MINITAB%denver@sri-unix.UUCP (02/17/84)

I am running Xenix on a TRS Model 16B.  There appears to be no stty
control call to send out a BREAK.   Anybody have any other ideas?

scw%ucla-locus@cepu.UUCP (02/17/84)

From:  Steve Woods <cepu!scw@ucla-locus>


	From:  RMark.MINITAB@denver
	>I am running Xenix on a TRS Model 16B.  There appears to be no stty
	>control call to send out a BREAK.   Anybody have any other ideas?
Here is some code that I put into our version of cu.c (we needed to
send break to talk to a IBM system <TSO loses>. Note that you need to
be able to switch speeds on the line for this to work.  An 'official'
break is supposed to be 250 Milliseconds long <it says here in the fine
print> but almost any UART reports the same thing when it gets a
framing error (12 bit times with no stop bit).

**************near  the top (a discription)***********************
/*
 *	~Bn	uucico sytle break (at 150 baud send n(1) nulls)
 *	~b	same as ~B3
 *	~@	attempt a real break (1 null at 1/2 speed)
 */
***********further on (the actuall code)*****************
/* this is on a switch on the character after the '~'*/
		case '@':
			{
			    int speed,stat,newspeed;
			    struct sgttyb stbuf;
			    struct sgttyb *st;
			    st = &stbuf;
			    ioctl(ln,TIOCGETP,st);
			    speed=stbuf.sg_ispeed; 
			    switch(speed){
				case B9600:
				case B4800:
				case B1200:
				case B600:
					newspeed= speed-1;
					break;
				default:
					newspeed = speed-2;
					break;
			    }
			    stbuf.sg_ispeed=stbuf.sg_ospeed=newspeed;
			    ioctl( ln,TIOCSETP, st);
			    write(ln,"\0",1);
			    stbuf.sg_ispeed=stbuf.sg_ospeed = speed;
			    ioctl( ln,TIOCSETP, st);
			}
			break;

		case 'B':
		case 'b':
			/* do a uucico style break 
			 * 'B' at 150 baud 1 null
			 *     or if Bn n nulls
			 * 'b' at 150 baud 3 null (real uucico style).
			 */
			{
			    int speed,stat,newspeed,nbreaks;
			    struct sgttyb stbuf;
			    struct sgttyb *st;
			    st = &stbuf;
			    ioctl(ln,TIOCGETP,st);
			    speed=stbuf.sg_ispeed; 
			    newspeed=B150;
			    if( b[1] == 'B'){
				if(b[2] > '0' && b[2] <= '9')nbreaks=b[2]-'0';
				else nbreaks=1;
			    }
			    else nbreaks=3;
			    stbuf.sg_ispeed=stbuf.sg_ospeed=newspeed;
			    ioctl( ln,TIOCSETP, st);
			    write(ln,"\0\0\0\0\0\0\0\0\0",nbreaks);
			    stbuf.sg_ispeed=stbuf.sg_ospeed = speed;
			    ioctl( ln,TIOCSETP, st);
			}
			break;

The switch on the sg_ispeed depends on the 'standard' available speeds
and values for them being in the standard order.
--
Stephen C. Woods (VA Wadsworth Med Ctr./UCLA Dept. of Neurology)
uucp:	...{ hao, trwrb, sdcsvax!bmcg}!cepu!scw   ARPA: cepu!scw@ucla-locus
location: N 34 06'37" W 118 25'43"

smk@axiom.UUCP (Steven M. Kramer) (02/20/84)

In 4.1BSD, you couldn't send an ioctl() unless the terminal were open
for writing (reading didn't matter).  If the same holds for USG, then
the little break program is broken.  If not, there is a UNIX incompatibility
(one among many).
-- 
	--steve kramer
	{allegra,genrad,ihnp4,utzoo,philabs,uw-beaver}!linus!axiom!smk	(UUCP)
	linus!axiom!smk@mitre-bedford					(MIL)

magi@deepthot.UUCP (David Wiseman) (02/20/84)

Watch those breaks! For those of you who are unable to generate breaks
(either because your kernel won't or you don't have sources to do it
yourself) you may be in trouble. I strongly suggest that if possible
you get your switch changed, we did. Although we can generate breaks
if necessary we have  found that switching equipment (or autobaud
detectors) are much too tempermental (mostly temper, partly mental)
for most people. Even users at terminals had difficulty convincing
the switches that they had actually "typed" a break. 

We eventually got the switch changed. It turns out that there are other
ways that switches are/can be configured to watch for terminals. We are
now using a DTR sense method which never fails. This has also
made it much easier for our machines to talk back out through the
switch; simple opens and closes (with appropriate wiring of the data line)
get and drop its attention. Admittedly, this is a feature of the switch
but...

If you absolutely MUST generate a break the only sure fire way is a small
"break box" which sits on the data line and generates a break when its
button is pressed. This isn't an elegant solution but it does work. Such
boxes are available from various suppliers and your friendly neighbourhood
maintenance types should be able to whip one up for you.

Although it is true that "close approximations" will work some of the
time I have found that they don't work enough of the time. And, in fact,
some equipment is too "smart" to be fooled in this manner.

When all else fails, change the hardware.

	...!utzoo!uwo!deepthot!watmath!...
		   !	 !
		 magi	magi

	(David Wiseman @ UWO Comp Sci, London Canada)

guy@rlgvax.UUCP (Guy Harris) (02/21/84)

Berkeley UNIX is the only "major" version which puts "file descriptor must
be open for reading/writing" restrictions on "ioctl"s.  S3/S5 don't, but
then again, neither did V7.

	Guy Harris
	{seismo,ihnp4,allegra}!rlgvax!guy

john@genrad.UUCP (John Nelson) (02/21/84)

You could always try setting the baud rate as low as possible
(50 baud?) and transmitting a NULL

ron%brl-vgr@sri-unix.UUCP (02/23/84)

From:      Ron Natalie <ron@brl-vgr>

The world famous kludge is to stty to the slowest possible speed
(and even parity or no parity if possible) and send a NUL.  In the
time frame of higher speed frames this looks pretty enough like a
break to satisfy most systems.

-Ron

stevel@haddock.UUCP (02/28/84)

#R:sri-arpa:-1681000:haddock:16700013:000:364
haddock!stevel    Feb 27 10:30:00 1984

Most serial drivers for UNIX system III/V send a break if the
speed is set to zero. I don't know about V7 or ZENIX, which is
a highly modified V7.

Steve Ludlum, decvax!yale-co!ima!stevel, {ucbvax|ihnp4}!cbosgd!ima!stevel
decwrl!amd70!ima!stevel, {uscvax|ucla-vax|vortex}!ism780!stevel
Interactive Systems, 7th floor, 441 Stuart st, Boston, MA 02116; 617-247-1155

swatt@ittvax.UUCP (02/28/84)

Guy Harris writes:

	Berkeley UNIX is the only "major" version which puts "file
	descriptor must be open for reading/writing" restrictions on
	"ioctl"s.  S3/S5 don't, but then again, neither did V7.

This is not true for 4.1; I haven't seen 4.2.  The code in "tty.c"
for the "ttioctl" function has a comment to the effect that if the
ioctl function changes the behavior of the device, insist on write
permission and suspend background processes.  However, the code to
enforce the write permission requirement is commented out.  The
manual page for ioctl(2) incorrectly claims the behavior Guy noted.

Has this changed in 4.2?

	- Alan S. "always insist on sources!" Watt

geoff@callan.UUCP (Geoff Kuenning) (04/01/84)

>	Most serial drivers for System III/V send a break if the line speed
>	is set to zero.
		- Steve Ludlum

Oh, yeah?  The ones I have used hang up the phone (by dropping DTR) when you
set the speed to zero.  Now that qualifies as a *HEFTY* break!

mcferrin@inuxc.UUCP (P McFerrin) (04/06/84)

#  From: john@genrad.UUCP (John Nelson)
#  Newsgroups: net.unix
#  Subject: Re: transmitting BREAK
#  Date: Tue, 21-Feb-84 09:00:44 EST
#  Article-I.D.: genrad.3864
#  Organization: GenRad, Bolton, Mass.
#  
#  You could always try setting the baud rate as low as possible
#  (50 baud?) and transmitting a NULL

A NULL is all zero's.  You really want a DEL (0377).

rpw3@fortune.UUCP (04/08/84)

#R:sri-arpa:-1674800:fortune:26900039:000:2930
fortune!rpw3    Apr  7 20:36:00 1984

Sorry, Mcferrin, Nelson is right.

While it is true that a <NUL> is all zeroes and a <DEL> is all ones,
the idle state of RS-232 data lines is MARK == ONE == +Volts.  A start
bit is a SPACE == ZERO == -Volts, and stop bits are ones.  Therefore,
if you want a big wide BREAK == "long space" == "long zeroes", better
send a slow <NUL>.

This is a historical anomaly left over, would you believe, from the original
days of the telegraph! Back then, everybody was wired in series (an arrangement
called "current loop" still seen in Teletype-based systems), and the idle
state of the line was with everybody's key shorted (closed) with that little
horizontal knife switch you see on the side of Morse Code keys.  To send, you
opened the switch (broke the line), and then sent. The "down" (or closed)
position of the key made a sound on the clicker or a "mark" on the paper
(for automatic strip paper recorders).  The "up"/open position made a "space"
on the paper. So the idle or "stop" state was "mark" and the "start" signal
(for the recorders) was "space". (The recorders shut off automatically on
"long mark").

Also, to interrupt someone who was sending (perhaps to send some priority
message like "Help! Robbers!"), you "broke" the line with your knife switch
(sent a <BREAK> or a "long space"). Because all the keys and clickers and
recorders were wired in series, the person who was sending would suddenly
be unable to hear his own "echo", so he (presumably) would stop and wait
for the "breaker" to send.

Note:	Timesharing systems that support half-duplex current-loop
	terminals (not "local copy", but true half-duplex with both
	keyboard and printer in series on the same pair of wires) have
	to expect everything they send to be "echoed" and have to use
	<BREAK> as the sole means of interrupting typeout. (They detect
	the <BREAK> by comparing what is sent out to the echo and assuming
	any difference is a <BREAK>. Thank goodness those are mostly gone!)

Anyway, the tradition lingered through 5-level teletypes (Model 19, etc.),
through 8-level ASCII tty's (Model 33/35/37) all of which used "current loop"
circuits. When the switch was made to "voltage" circuits (RS-232), in order
to allow current-loop to RS-232 level converters to work, RS-232 had to use
the same conventions. To add to the confusion, the CONTROL leads use the same
ONE == +V / ZERO == -V convention as the DATA leads, all right, but the control
leads don't have the concept of mark and space. So the idle condition for
control lines like RING and DTR is zero (or -V). Just backwards from data.

See John McNamara's "Technical Aspects of Data Communications" (DIGITAL Press)
for more amusing historical tidbits (like Strowger the undertaker and the
first dial telephone).

Rob Warnock

UUCP:	{ihnp4,ucbvax!amd70,hpda,harpo,sri-unix,allegra}!fortune!rpw3
DDD:	(415)595-8444
USPS:	Fortune Systems Corp, 101 Twin Dolphin Drive, Redwood City, CA 94065

jerry@oliveb.UUCP (Jerry Aguirre) (04/09/84)

With regard to sending a NULL at 50 BAUD to simulate a break:
mcferrin@inuxc.UUCP (P McFerrin) says:

    A NULL is all zero's.  You really want a DEL (0377).

Actually you do want a NULL.  The idle state for an rs232 line is the
mark or all ones state (for "historical" reasons which I suspect date
back to the days of current loop).  A break consists of forcing the
line into the all zero state for more than one character time.

------        ......................................------//--
      | start .                                    . stop     | next
 idle | bit   .   your character  with parity      . bit      | start
  1   |  0    .                                    .  1       | bit
       -------......................................           -----

The only thing sending a 0377 would do is maybe send a break because of
the zero start bit.  I have tried the approach of sending a NULL at 50
BAUD and it works well enough to toggle the 1200/300 BAUD rate.
Actually an '@' (0100) will work nearly as well.

But keep in mind that a break is not always a break.  Some hardware
requires a longer break before it will take notice.  Our PDP-11/70 will
toggle BAUD rate on a 50 BAUD NULL but our Micom port selector will not
break the connection.  It apparently requires a longer break.  Check out
any modem or other data communication equipment that requires a break.
They may have a minimum break time specified in the specs.

					    Jerry Aguirre
    {hplabs|fortune|ios|tolerant|allegra|tymix}!oliveb!jerry

hull@hao.UUCP (Howard Hull) (04/10/84)

I take exception with respect to Rob Warnock's (!fortune!rpw3) statement:
     Sorry, Mcferrin, Nelson is right.

     While it is true that a <NUL> is all zeroes and a <DEL> is all ones,
>>>>>the idle state of RS-232 data lines is MARK == ONE == +Volts.  A start
>>>>>bit is a SPACE == ZERO == -Volts, and stop bits are ones.  Therefore,
     if you want a big wide BREAK == "long space" == "long zeroes", better
     send a slow <NUL>.
doesn't seem to ring true for the RS232 coming out of pin 2 of my terminal.
An oscilloscope shows the idle state at -12 volts (MARKING) is the level for
logical ONE ; the +12 volt state (SPACING) is for logical ZERO.  The additional
information can be added to Jerry Aguirre's contribution (thanks for accurate
graphics, Jerry):

-12V ------        ......................................------//--        MK
           | start .                                    . stop     | next
 0V   idle | bit   .   your character  with parity      . bit      | start
       1   |  0    .                                    .  1       | bit
+12V        -------......................................           -----  SP

So you can either be positively logical, or stand on your head when you look
at your oscilloscope.				Howard Hull	!hao!hull

rpw3@fortune.UUCP (04/11/84)

#R:sri-arpa:-1674800:fortune:26900042:000:1559
fortune!rpw3    Apr 11 03:06:00 1984

+--------------------
| I forgot about the inversion.  A NULL is correct.  However,
| the idle state of a RS232 line is MARK = ONE = -V.
|                                                ^^
| The rs232 interface spec defines a -V as a binary state of 1 or MARK.
| 
| 				Paul McFerrin
+--------------------

Wow, is my face red! (*BLUSH*)

In my rush to correct Mr. McFerrin and in my enthusiasm for a bit of
history, I goofed (badly). He is, of course, correct. The idle state for
ALL signal lines, data and control, on an RS-232 connection is "-V"
(= ONE = MARK = "stop-bit").  "+V" is actually SPACE = ZERO = "start-bit".

[When one is working with the TTL levels corresponding to an RS-232 interface,
there is generally a layer of inverters involved, so on the TTL side, the data
is MARK = ONE = +TTL and SPACE = ZERO = ~GND. If you look at the pretty little
picture "oliveb!jerry" drew, you will see a start-bit going LOW, just like
I'm used to watching it on a 'scope. On the other hand, the control signals
are usually low-asserted on the TTL side, so I have no excuse.]

Anyway... the point of the story was to give some background/insight as to the
reason the data lines use "-V" to mean "one", not "zero", just the opposite of
the control lines (assuming you call an active control line "one").

(I've just GOT to be more careful... I've only been doing this for 20 years!)

Rob Warnock

UUCP:	{ihnp4,ucbvax!amd70,hpda,harpo,sri-unix,allegra}!fortune!rpw3
DDD:	(415)595-8444
USPS:	Fortune Systems Corp, 101 Twin Dolphin Drive, Redwood City, CA 94065