Path: utzoo!attcan!uunet!snorkelwacker!tut.cis.ohio-state.edu!rutgers!mcnc!rti!mozart!walker From: walker@unx.sas.com (Doug Walker) Newsgroups: comp.sys.amiga Subject: Re: program question, stdin, stdout. Message-ID: <1990Aug02.190939.21710@unx.sas.com> Date: 2 Aug 90 19:09:39 GMT References: <2033@bnlux0.bnl.gov> Organization: SAS Institute Inc. Lines: 296 In article <2033@bnlux0.bnl.gov> kushmer@bnlux0.bnl.gov (christopher kushmerick) writes: >main() >{ > while ((c=getchar())!=EOF) putchar(c); >} > > >When I replace putchar with printf("%d\n",c) the program works as I woud >expect, it prints out the ascii value of the character I hit. Getchar and putchar are both buffered. To make them unbuffered, use the rawio functions that Chuck McManis did a few years back, on a low-numbered fish disk, or ConsoleIO by Jim Cooper on disk 69. here's Chuck's stuff: Many times I have wanted to set 'stdin' in my programs to what is often referred to as 'CBREAK' mode. Basically, that means that every time you call getchar() you get a character. Up until now there was no easy way to do that. The enclosed shar file contains three files, testraw.c raw.c and sendpacket.c. The interesting one is raw.c which contains the functions raw() and cooked(). These take a file pointer (FILE *) and convert it to raw mode or cooked mode respectively. The testraw.c file shows how it is done. Note that this will probably only work for Lattice users since it uses the Lattice ios1.h file to find the DOS FileHandle associated with a 'Level 2' file. Anyway, it was short so it is included here complete. --Chuck McManis uucp: {anywhere}!sun!cmcmanis BIX: cmcmanis ARPAnet: cmcmanis@sun.com These opinions are my own and no one elses, but you knew that didn't you. ------------------------------CUT HERE-------------------------------- /* * raw.c * * This is a routine for setting a given stream to raw or cooked mode. * This is useful when you are using Lattice C to produce programs that * want to read single characters with the "getch()" or "fgetc" call. * * Written : 18-Jun-87 By Chuck McManis. * If you use it I would appreciate credit for it somewhere. */ #include #include #include #include #include #include /* New Packet in 1.2 */ #define ACTION_SCREEN_MODE 994L extern int errno; /* The error variable */ /* * Function raw() - Convert the specified file pointer to 'raw' mode. This * only works on TTY's and essentially keeps DOS from translating keys for * you, also (BIG WIN) it means getch() will return immediately rather than * wait for a return. You lose editing features though. */ long raw(fp) FILE *fp; { struct MsgPort *mp; /* The File Handle message port */ struct FileHandle *afh; struct UFB *ufb; long Arg[1],res; ufb = (struct UFB *) chkufb(fileno(fp)); /* Step one, get the file handle */ afh = (struct FileHandle *)(ufb->ufbfh); if (!IsInteractive(afh)) { /* Step two, check to see if it's a console */ errno = ENOTTY; return(-1); } /* Step three, get it's message port. */ mp = ((struct FileHandle *)(BADDR(afh)))->fh_Type; Arg[0] = -1L; res = SendPacket(mp,ACTION_SCREEN_MODE,Arg,1); /* Put it in RAW: mode */ if (res == 0) { errno = ENXIO; return(-1); } return(0); } /* * Function - cooked() this function returns the designate file pointer to * it's normal, wait for a mode. This is exactly like raw() except that * it sends a 0 to the console to make it back into a CON: from a RAW: */ long cooked(fp) FILE *fp; { struct MsgPort *mp; /* The File Handle message port */ struct FileHandle *afh; struct UFB *ufb; long Arg[1],res; ufb = (struct UFB *) chkufb(fileno(fp)); afh = (struct FileHandle *)(ufb->ufbfh); if ( ! IsInteractive(afh)) { errno = ENOTTY; return(-1); } mp = ((struct FileHandle *)(BADDR(afh)))->fh_Type; Arg[0] = 0; res = SendPacket(mp,ACTION_SCREEN_MODE,Arg,1); if (res == 0) { errno = ENXIO; return(-1); } return(0); } ------------------------------CUT HERE-------------------------------- /* * testraw.c * * This program shows how to use the functions raw() and cooked() to * control the way characters are read from a Level 2 file pointer. * These are only useful if the file pointer points at an instance of * the console.device, which means one of 'stdin', 'stdout', or 'stderr' * or a console opened with fp = fopen("CON:x/y/wid/len/Title","w+"); * like this example does. * * Written : 16-Jun-87 By Chuck McManis, do with it what you will. * */ #include #ifndef u_char #define u_char unsigned char #endif void main() { FILE *win; char c; long i; printf("This program shows how to use raw mode file pointers.\n"); printf("First we open the window...\n"); win = fopen("CON:10/10/400/100/Test Console","w+"); /* If opening a file, use setnbf() to set it to unbuffered mode, this is * very importatant. Not required for stdin since Lattice defaults it to * unbuffered. */ setnbf(win); fprintf(win,"Using the default mode, type some characters ... \n"); fprintf(win,"Type a 'Q' to go to next phase ... \n"); i = 0; while ((c = fgetc(win)) != 'Q') { i = (i + 1) % 25; if (i == 0) printf("\n"); printf(" %02x",(u_char) c); } printf("\n************\n"); fprintf(win,"Now switching to 'raw' mode ...\n"); fprintf(win,"Type a 'Q' to go to next phase ... \n"); if (raw(win) != 0) perror("raw"); i = 0; while ((c = fgetc(win)) != 'Q') { i = (i + 1) % 25; if (i == 0) printf("\n"); printf(" %02x",(u_char) c); } printf("\n************\n"); fprintf(win,"Now back to 'cooked' mode ... \n"); fprintf(win,"Type a 'Q' to quit ... \n"); if (cooked(win) != 0) perror("cooked"); i = 0; while ((c = fgetc(win)) != 'Q') { i = (i + 1) % 25; if (i == 0) printf("\n"); printf(" %02x",(u_char) c); } fclose (win); } ------------------------------CUT HERE-------------------------------- /* * Sendpacket.c * * An invaluable addition to your Amiga.lib file. This code sends a packet * the given message port. This makes working around DOS lots easier. * * Note, I didn't write this, those wonderful folks at CBM did. I do suggest * however that you may wish to add it to Amiga.Lib, to do so, compile it * and say 'oml lib:amiga.lib -r sendpacket.o' */ #include #include #include #include #include /* * Function - SendPacket written by Phil Lindsay, Carolyn Scheppner, and * Andy Finkel. This function will send a packet of the given type to the * Message Port supplied. */ long SendPacket(pid,action,args,nargs) struct MsgPort *pid; /* process indentifier ... (handlers message port ) */ long action, /* packet type ... (what you want handler to do ) */ args[], /* a pointer to a argument list */ nargs; /* number of arguments in list */ { struct MsgPort *replyport; struct StandardPacket *packet; long count, *pargs, res1; replyport = (struct MsgPort *) CreatePort(NULL,0); if(!replyport) return(0); /* Allocate space for a packet, make it public and clear it */ packet = (struct StandardPacket *) AllocMem((long)sizeof(struct StandardPacket),MEMF_PUBLIC|MEMF_CLEAR); if(!packet) { DeletePort(replyport); return(0); } packet->sp_Msg.mn_Node.ln_Name = (char *)&(packet->sp_Pkt); packet->sp_Pkt.dp_Link = &(packet->sp_Msg); packet->sp_Pkt.dp_Port = replyport; packet->sp_Pkt.dp_Type = action; /* copy the args into the packet */ pargs = &(packet->sp_Pkt.dp_Arg1); /* address of first argument */ for(count=0;count < nargs;count++) pargs[count]=args[count]; PutMsg(pid,packet); /* send packet */ WaitPort(replyport); GetMsg(replyport); res1 = packet->sp_Pkt.dp_Res1; FreeMem(packet,(long)sizeof(struct StandardPacket)); DeletePort(replyport); return(res1); } ------------------------------CUT HERE-------------------------------- OBJ = raw.o sendpacket.o testraw.o CC = lc CFLAGS = -cwusf -d -E testraw : $(OBJ) blink lib:c.o $(OBJ) to testraw lib lib:lc.lib lib:amiga.lib sc sd verbose testraw.o: testraw.c sendpacket.o: sendpacket.c raw.o: raw.c .c.o : $(CC) $(CFLAGS) $* ------------------------------CUT HERE-------------------------------- Article 5545 of comp.sys.amiga: Path: mcdsun!noao!hao!husc6!mit-eddie!genrad!decvax!decwrl!pyramid!oliveb!sun!pepper!cmcmanis From: cmcmanis%pepper@Sun.COM (Chuck McManis) Newsgroups: comp.sys.amiga Subject: Set your console to raw mode Keywords: cbreak() raw() cooked() Message-ID: <21174@sun.uucp> Date: 16 Jun 87 09:09:27 GMT Sender: news@sun.uucp Lines: 256 Many times I have wanted to set 'stdin' in my programs to what is often referred to as 'CBREAK' mode. Basically, that means that every time you call getchar() you get a character. Up until now there was no easy way to do that. The enclosed shar file contains three files, testraw.c raw.c and sendpacket.c. The interesting one is raw.c which contains the functions raw() and cooked(). These take a file pointer (FILE *) and convert it to raw mode or cooked mode respectively. The testraw.c file shows how it is done. Note that this will probably only work for Lattice users since it uses the Lattice ios1.h file to find the DOS FileHandle associated with a 'Level 2' file. Anyway, it was short so it is included here complete. --Chuck McManis uucp: {anywhere}!sun!cmcmanis BIX: cmcmanis ARPAnet: cmcmanis@sun.com These opinions are my own and no one elses, but you knew that didn't you.