Let the Sun-3 beep! How???

Let the Sun-3 beep! How???

Post by ch.. » Mon, 02 Apr 1990 01:49:00



In article <1...@ames.UUCP> wat...@ames.UUCP (John S. Watson) writes:

>Here is a morse code program for Sun workstations.

John's program works, but, being a fan of data structures, I had
to rewrite it.  Also, his tends to use inordinate amounts of CPU
time, to run at different speeds on different kinds of Suns, and
to sound somewhat lopsided if you had something in the background.
Moreover, if you interrupted it, it might leave the bell on, which
is decidedly annoying.

This version's output is essentially identical.  The single optional
argument specifies the number of milliseconds for the basic time
unit (default 30).  The Sun timer resolution is somewhat low, and
values between 21 and 30 all act the same, and 20 runs 50% faster
than these; this is an annoyance, but it does keep the CPU time
down.

/*
 * Morse Code Program for Suns
 *
 * Inspired by version by:
 *      John S. Watson  4/29/87
 *      NASA Ames Research Center
 *      ARPA:  wat...@ames.arpa
 *      UUCP:  ...!ames!watson
 *
 * This version by:
 *      Chris Torek  4/29/87
 *      University of Maryland
 *      Department of Computer Science
 *      (ch...@mimsy.umd.edu)
 */

#include <stdio.h>
#include <ctype.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/file.h>
#include <sys/time.h>
#include <sundev/kbd.h>
#include <sundev/kbio.h>

/*
 * Morsetab[] contains the `visual form' rendition of each known
 * character.  All other characters act as word separators, hence
 * there is no need for an entry for space.
 *
 * The encode() function puts a pointer to the valid codes in the
 * table codetab[]; the invalid ones remain NULL.  The code translation
 * table is 256 entries, and the initialisation of the array is
 * portable to EBCDIC (among others).
 *
 * N.B.: all of the code values in morsetab[] must be valid input
 * character codes.
 */
struct morse {
        int     m_code;         /* the input character (lowercase) */
        char    *m_rend;        /* and its rendition */

} morsetab[] = {

        'a',    ".-",
        'b',    "-..",
        'c',    "-.-.",
        'd',    "-..",
        'e',    ".",
        'f',    "..-.",
        'g',    "--.",
        'h',    "....",
        'i',    "..",
        'j',    ".---",
        'k',    "-.-",
        'l',    ".-..",
        'm',    "--",
        'n',    "-.",
        'o',    "---",
        'p',    ".--.",
        'q',    "--.-",
        'r',    ".-.",
        's',    "...",
        't',    "-",
        'u',    "..-",
        'v',    "...-",
        'w',    ".--",
        'x',    "-..-",
        'y',    "-.--",
        'z',    "--..",
        '0',    "-----",
        '1',    ".----",
        '2',    "..---",
        '3',    "...--",
        '4',    "....-",
        '5',    ".....",
        '6',    "-....",
        '7',    "--...",
        '8',    "---..",
        '9',    "----.",
        ',',    "--..--",
        '.',    ".-.-.-",
        -1,     NULL            /* end marker */

};

char    *codetab[256];

/* convert X to milliseconds (in scale factors) */
#define MS(x)   ((x) * 1000)

char    *progname;
long    scale = MS(30);

int     keyboard;
int     bell_on = KBD_CMD_BELL;
int     bell_off = KBD_CMD_NOBELL;
#define FEEP()          (void) ioctl(keyboard, KIOCCMD, (char *) &bell_on)
#define UNFEEP()        (void) ioctl(keyboard, KIOCCMD, (char *) &bell_off)

/*
 * Pause for number counts.  Number must not be `large'.
 */
unit_pause(number)
        int number;
{
        struct timeval tv;
#define USEC 1000000            /* microseconds per second */

        /* this value may be >= 1e6 */
        tv.tv_usec = number * scale;
        tv.tv_sec = tv.tv_usec / USEC;
        tv.tv_usec -= tv.tv_sec * USEC;
        (void) select(0, (int *)0, (int *)0, (int *)0, &tv);

}

/*
 * Do a dit (if it) or dah (if not).
 */
d(it)
        int it;
{

        FEEP();
        unit_pause(it ? 1 : 3);
        UNFEEP();
        unit_pause(1);

}

/*
 * Build the input character translation table.
 */
encode()
{
        register struct morse *p;
        register int i;

        for (p = morsetab; p->m_rend != NULL; p++) {
                i = p->m_code;
                if (codetab[i] != NULL)
                        goto bug;
                codetab[i] = p->m_rend;
                if (islower(i)) {
                        i = toupper(i);
                        if (codetab[i] != NULL) {
bug:
                                (void) fprintf(stderr,
                                        "%s: panic: codetab[%d] != NULL\n",
                                        progname, i);
                                exit(1);
                        }
                        codetab[i] = p->m_rend;
                }
        }

}

init_keyboard()
{

        keyboard = open("/dev/kbd", O_RDWR, 0666);
        if (keyboard < 0) {
                (void) fprintf(stderr, "%s: cannot open ", progname);
                perror("/dev/kbd");
                exit(1);
        }

}

/*
 * `Print' the contents of file f in morse code.
 */
morse(f)
        register FILE *f;
{
        register int c;
        register char *mp;
        int inword = 0;

        while ((c = getc(f)) != EOF) {
                if ((mp = codetab[c]) == NULL) {
                        if (inword) {
                                unit_pause(5);
                                inword = 0;
                        }
                        continue;
                }
                inword = 1;
                while ((c = *mp++) != 0)
                        d(c == '.');
                unit_pause(2);
        }

}

catch()
{

        UNFEEP();
        exit(1);

}

set(sig, disp)
        int sig, (*disp)();
{

#if defined(sun) && defined(lint)
        /* Sun 3.0 lint library is wrong */
        if (signal(sig, (void (*)()) SIG_IGN) != SIG_IGN)
                (void) signal(sig, (void (*)()) disp);
#else
        if (signal(sig, SIG_IGN) != SIG_IGN)
                (void) signal(sig, disp);
#endif

}

main(argc, argv)
        int argc;
        char **argv;
{

        progname = argv[0];
        set(SIGHUP, catch);
        set(SIGQUIT, catch);
        set(SIGINT, catch);
        set(SIGTERM, catch);

        if (argc >= 2) {
                scale = MS(atoi(argv[1]));
                if (scale < MS(1)) {
                        (void) fprintf(stderr,
                                "%s: can't go that fast\n", progname);
                        exit(1);
                }
        }
        init_keyboard();
        encode();
        morse(stdin);
        exit(0);

}

--
In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7690)
Domain: ch...@mimsy.umd.edu     Path:   seismo!mimsy!chris
 
 
 

Let the Sun-3 beep! How???

Post by Akka » Mon, 02 Apr 1990 17:14:00


I'm new to this newsgroup, so I may have missed a posting, but ...

I know about KBD_CMD_BELL and all that -- found it in the manual
and wrote a * beep routine for the Sun console -- but am I
the only one in the world bothered by the fact that ^G doesn't beep
a Sun console the way it does (practically) ever other terminal
ever made?  I've complained to Sun numerous times about how my
3/160 console doesn't beep when I print a ^G -- which means that
programs like talk and vi can't notify me, because THEY don't do
the kbd ioctl, and also that I won't be notified if I'm rlogged in
from another Sun, because if I try to do the ioctl it will come
out on the wrong screen.  Finally, it means that in all my programs
I have to do something like
#ifdef sun
#include <sundev/kbd.h>
#include <sundev/kbio.h>
#endif
.
.
#ifdev KBD_CMD_BELL     /* if we're on a Sun3, or at least 3.x */
if (on_console)         /* Need to check at beginning of program
                         * to make sure we're on the console so
                         * we don't beep it if someone else is on it
                         */
        ioctl( ...etc )
else
#else
        putchar('\07');
#endif

I mean, it wasn't that hard to figure out, but it's a little
inelegant to have to put that into every single program,
and Sun didn't do it when they wrote talk and vi.

After six months of hearing me talk about it, the local Sun reps
finally told me that there was an ECO which would fix the problem,
and came out to install a new CPU board (note that I had to be on
hardware maintenance to get this fixed).  A week and two CPU
boards later (the first one they sent out didn't work, and it
took several hours to get the second one working, for some reason)
I finally had a machine which supposedly beeped -- and guess what?
It's still barely audible -- too short and too quiet to be heard
when I'm standing across the room (i.e. talk still can't notify
me when someone's trying to talk to me).  And echoing several ^G's
is even less audible than echoing just one.

The Sun2/170 (2.2) I used to use had a wonderful ^G -- it was nice
and loud without being too obnoxious, and if I wanted something
really obnoxious I could always say "echo ^G^G^G^G^G^G^G^G^G^G^G^G^G^G"
and get a long, continuous bell which I couldn't fail to hear.
I'd like to be able to do that on my Sun3 without having to write
a C program (and compile it into all the system programs and PD
programs off the net and so forth) to do it.  Isn't anyone else
bothered by it?  I'm sure it's an easy fix -- I've asked Sun several
times why it isn't possible simply to take the source for the console
driver, find the part where it interprets a ^G, lengthen the time
before the KBD_CMD_NOBELL ioctl, and recompile; Sun is convinced
that it's a hardware problem and changing software won't help it.
Has anybody with source tried it?  (We're in the process of trying
to get source, but it hasn't happened yet.)  Is there something
wrong with my reasoning?  Is it really a hardware problem?  Do
other 3.x Sun3's beep loudly, and mine just happens to have a
strange problem?

..
        ...Akkana         Center for Nonlinear Studies, LANL

"I think I'll take a walk.  Hmm, wonder where this wire goes?"
                        -- Max Headroom

 
 
 

1. Let the Sun-3 beep! How??? - (nf)

Subject: Bell on SUN-3 Workstation

Apparently, it is impossible to let the Sun console beep without using
`window_bell'. Does anybody out there know of a possiblity other than this
function (e.g. by accessing the keyboard bell) to generate a beep?

Juergen Wagner,              (USENET) ...seismo!unido!iaoobel!wagner
("Gandalf")                    Fraunhofer Institute IAO, Stuttgart

2. Security Vulnerability with DESMS

3. Sun Unix OS won't let me write beeps faster than 1.5 seconds apart

4. Error occurs when starting xarchie and xgopher

5. beep, beep, beep

6. troubles with rlfossil

7. let unix beep

8. Imagemap Support httpd.tgz

9. Beep, beep...

10. AMI BIOS Beep Codes (was dead PC beeps 8 times)

11. Q: How to beep w/o calling beep()?

12. Beep Beep

13. keyboard beep on sun type 4 keyboard