Need to write putchar for embedded system

Discussion in 'C Programming' started by Confused User, Jul 1, 2005.

  1. I am working on device that utilizes a Motorola 68HC16 microcontroller. I am
    using an old unsupported piece of crap Whitesmith's / Intermetrics / Tasking
    compiler. The embedded compiler business was quite insestual for while
    wasn't it? I need to write putchar so that printf can function properly.

    Anyway, the compiler comes with just a shell of a putchar routine. It
    literally returns the character you passed to it and nothing else. That is
    not why it's a piece of crap, although they could have at least supplied
    something that writes to the serial port.

    So, I already have a serial port interrupt routing with circular buffers
    (in/out) and a function call (SendData()) that copies a data from a pointer
    argument and manages the circular buffer. So, I want to have my putchar
    routine call SendData.

    I noticed from looking around that putchar returns EOF if unsuccessful. EOF
    is defined as -1 in the compiler header file. Therefore, it occurs to me
    that putchar can only be used for ASCII data. This is OK, I just need to
    make sure I have that right. Because, binary data could include -1 right?
    That means I should never use it alone to send binary data. If so, is this
    true for the PC? After all, it's counterpart, getchar retrives binary scan
    codes from the keyboard unless they have already been converted to ASCII
    characters before they get to that level.

    I would guess the only time getchar should return EOF is if the transmit
    buffer is full. My SendData() function already is set to return a fail code
    if the buffer is full. putchar can pass this on to printf (of course I have
    to change SendData() to use EOF as a fail code).

    As an embedded programmer, I am not real familiar with what normal pass/fail
    return codes should be. The high level languages were developed around full
    OS systems (Unix etc.) and then seem to have migrated to the embedded world
    leaving some us without familiarity of conventions.

    Enough rambling.... Just looking for any constructive input.

    Elvis
    Confused User, Jul 1, 2005
    #1
    1. Advertising

  2. >I am working on device that utilizes a Motorola 68HC16 microcontroller. I am
    >using an old unsupported piece of crap Whitesmith's / Intermetrics / Tasking
    >compiler. The embedded compiler business was quite insestual for while
    >wasn't it? I need to write putchar so that printf can function properly.


    >Anyway, the compiler comes with just a shell of a putchar routine. It
    >literally returns the character you passed to it and nothing else. That is
    >not why it's a piece of crap, although they could have at least supplied
    >something that writes to the serial port.


    Well, that assumes that everyone uses the serial port and not, for
    example, a keypad and 8-character LCD display, which I suppose
    someone could attach to this thing if, for example, it's going to
    run a microwave oven.

    >So, I already have a serial port interrupt routing with circular buffers
    >(in/out) and a function call (SendData()) that copies a data from a pointer
    >argument and manages the circular buffer. So, I want to have my putchar
    >routine call SendData.


    >I noticed from looking around that putchar returns EOF if unsuccessful. EOF
    >is defined as -1 in the compiler header file. Therefore, it occurs to me
    >that putchar can only be used for ASCII data. This is OK, I just need to
    >make sure I have that right. Because, binary data could include -1 right?


    putchar() can return -1 for EOF and (unsigned char)c for a character.
    Assuming that an int (must be at least 16 bits) has more bits than
    a char (must be at least 8 bits, but could be 16 or 32), there is
    no ambiguity here. Oh, yes, hardly anyone bothers to look at the
    return value of putchar() anyway.

    >That means I should never use it alone to send binary data. If so, is this
    >true for the PC? After all, it's counterpart, getchar retrives binary scan
    >codes from the keyboard unless they have already been converted to ASCII
    >characters before they get to that level.


    I don't know of any implementation in which getchar() returns scan
    codes unless you do something system-dependent, non-default, and
    obnoxious to cause that. Scan codes aren't characters. You need
    to combine the scan code(s) with shift states to get actual characters.

    >I would guess the only time getchar should return EOF is if the transmit
    >buffer is full.


    No. getchar() should return EOF if the implementation-defined
    end-of-file character is typed, if there even is such a character.
    Or perhaps if DCD drops. Depending on what you are using it for,
    a version of getchar() which *NEVER* returns EOF could be fine.

    putchar() should return EOF, well, almost never. Maybe if CTS
    drops. It should NOT return EOF because the program is sending
    data faster than you can get it out the serial port. In that
    situation it should WAIT. This could get complicated in a multi-tasking
    system where an interrupt that there is space in the buffer causes
    a thread/process/whatever to wake up. In a uni-tasking situation
    it's easy: busy wait for the buffer to become free, then send the
    character.

    >My SendData() function already is set to return a fail code
    >if the buffer is full. putchar can pass this on to printf (of course I have
    >to change SendData() to use EOF as a fail code).


    No, you don't have to change SendData() to use EOF as a buffer-full code.
    In putchar():
    if (SendData(foo) == ERROR_BUFFER_FULL) return EOF;

    Buffer full is not an error condition. Assuming you've got a
    processor that's less slow than pitiful for 20 years ago (e.g.
    100*K*Hz), any attempts to send a line of data bigger than the
    buffer size (16 characters?) is going to fill the buffer almost
    immediately.

    >As an embedded programmer, I am not real familiar with what normal pass/fail
    >return codes should be. The high level languages were developed around full
    >OS systems (Unix etc.) and then seem to have migrated to the embedded world
    >leaving some us without familiarity of conventions.
    >
    >Enough rambling.... Just looking for any constructive input.


    ANSI/ISO C does not have non-blocking I/O. That means you can't, using
    standard routines, wait to output something while scanning for input
    on something else. You might end up needing non-standard non-blocking
    routines for the serial port, depending on what you need to do.
    (SendData() might serve this purpose well as-is).

    It also means that getchar() and putchar() need to be written as
    blocking.

    Gordon L. Burditt
    Gordon Burditt, Jul 1, 2005
    #2
    1. Advertising

  3. Confused User

    Jack Klein Guest

    On Thu, 30 Jun 2005 21:29:48 -0400, "Confused User"
    <> wrote in comp.lang.c:

    Neither of the groups that you posted this to is optimum,
    news:comp.arch.embedded would probably have been better.

    > I am working on device that utilizes a Motorola 68HC16 microcontroller. I am
    > using an old unsupported piece of crap Whitesmith's / Intermetrics / Tasking
    > compiler. The embedded compiler business was quite insestual for while
    > wasn't it? I need to write putchar so that printf can function properly.


    There are other compilers available if you don't like that one.

    > Anyway, the compiler comes with just a shell of a putchar routine. It
    > literally returns the character you passed to it and nothing else. That is
    > not why it's a piece of crap, although they could have at least supplied
    > something that writes to the serial port.


    Your assumption is that it should write to the serial port. Others
    might have other ideas.

    > So, I already have a serial port interrupt routing with circular buffers
    > (in/out) and a function call (SendData()) that copies a data from a pointer
    > argument and manages the circular buffer. So, I want to have my putchar
    > routine call SendData.
    >
    > I noticed from looking around that putchar returns EOF if unsuccessful. EOF
    > is defined as -1 in the compiler header file. Therefore, it occurs to me
    > that putchar can only be used for ASCII data. This is OK, I just need to
    > make sure I have that right. Because, binary data could include -1 right?
    > That means I should never use it alone to send binary data. If so, is this
    > true for the PC? After all, it's counterpart, getchar retrives binary scan
    > codes from the keyboard unless they have already been converted to ASCII
    > characters before they get to that level.


    No, you are completely wrong about putchar() being for ASCII data
    only. putchar() converts the value it receives to unsigned char,
    which cannot be negative, and it returns that unsigned char. The
    implementation is free to define any negative int value for EOF,
    although -1 is extremely common.

    Now the value of an unsigned char, any unsigned char, is not
    equivalent to the int -1.

    > I would guess the only time getchar should return EOF is if the transmit
    > buffer is full. My SendData() function already is set to return a fail code
    > if the buffer is full. putchar can pass this on to printf (of course I have
    > to change SendData() to use EOF as a fail code).
    >
    > As an embedded programmer, I am not real familiar with what normal pass/fail
    > return codes should be. The high level languages were developed around full
    > OS systems (Unix etc.) and then seem to have migrated to the embedded world
    > leaving some us without familiarity of conventions.
    >
    > Enough rambling.... Just looking for any constructive input.


    Again, the putchar() function is called with an int, but it only uses
    CHAR_BIT bits out of that int, and it treats them as an unsigned char.
    On your implementation, that means the value it deals with is in the
    range 0 to 255, inclusive. None of these values is the same as the
    int value -1.

    --
    Jack Klein
    Home: http://JK-Technology.Com
    FAQs for
    comp.lang.c http://www.eskimo.com/~scs/C-faq/top.html
    comp.lang.c++ http://www.parashift.com/c -faq-lite/
    alt.comp.lang.learn.c-c++
    http://www.contrib.andrew.cmu.edu/~ajo/docs/FAQ-acllc.html
    Jack Klein, Jul 1, 2005
    #3
  4. Gordon & Jack,
    A lot of helpful input. Thanks a lot!
    I do want to elaborate on a few points and ask further questions, however,
    it is 8:30am and I have to get to work. This info will help me today.

    I will be back later for some further discussion on this topic.

    Thanks again,

    Elvis
    -------------------------------------------------------------------
    "Confused User" <> wrote in message
    news:X31xe.6050$...
    > I am working on device that utilizes a Motorola 68HC16 microcontroller. I

    am
    > using an old unsupported piece of crap Whitesmith's / Intermetrics /

    Tasking
    > compiler. The embedded compiler business was quite insestual for while
    > wasn't it? I need to write putchar so that printf can function properly.
    >
    > Anyway, the compiler comes with just a shell of a putchar routine. It
    > literally returns the character you passed to it and nothing else. That is
    > not why it's a piece of crap, although they could have at least supplied
    > something that writes to the serial port.
    >
    > So, I already have a serial port interrupt routing with circular buffers
    > (in/out) and a function call (SendData()) that copies a data from a

    pointer
    > argument and manages the circular buffer. So, I want to have my putchar
    > routine call SendData.
    >
    > I noticed from looking around that putchar returns EOF if unsuccessful.

    EOF
    > is defined as -1 in the compiler header file. Therefore, it occurs to me
    > that putchar can only be used for ASCII data. This is OK, I just need to
    > make sure I have that right. Because, binary data could include -1 right?
    > That means I should never use it alone to send binary data. If so, is this
    > true for the PC? After all, it's counterpart, getchar retrives binary scan
    > codes from the keyboard unless they have already been converted to ASCII
    > characters before they get to that level.
    >
    > I would guess the only time getchar should return EOF is if the transmit
    > buffer is full. My SendData() function already is set to return a fail

    code
    > if the buffer is full. putchar can pass this on to printf (of course I

    have
    > to change SendData() to use EOF as a fail code).
    >
    > As an embedded programmer, I am not real familiar with what normal

    pass/fail
    > return codes should be. The high level languages were developed around

    full
    > OS systems (Unix etc.) and then seem to have migrated to the embedded

    world
    > leaving some us without familiarity of conventions.
    >
    > Enough rambling.... Just looking for any constructive input.
    >
    > Elvis
    >
    >
    Confused User, Jul 1, 2005
    #4
  5. Confused User

    pete Guest

    Jack Klein wrote:

    > putchar() converts the value it receives to unsigned char,
    > which cannot be negative, and it returns that unsigned char.


    putchar(-1) wouldn't return that unsigned char,
    if sizeof(int) was equal to 1.

    If putchar(-1) doesn't return EOF,
    then it returns ((int)(unsigned char)-1).

    --
    pete
    pete, Jul 8, 2005
    #5
  6. Confused User

    Old Wolf Guest

    Confused User wrote:
    > I am working on device that utilizes a Motorola 68HC16 microcontroller.
    > I am using an old unsupported piece of crap Whitesmith's / Intermetrics
    > / Tasking compiler. The embedded compiler business was quite insestual
    > for while wasn't it?


    The C standard allows for embedded systems (aka. freestanding
    implementations), and they aren't required to implement
    any of the I/O functions in the C library.

    >I need to write putchar so that printf can function properly.
    > Anyway, the compiler comes with just a shell of a putchar routine.
    > It literally returns the character you passed to it and nothing else.
    > That is not why it's a piece of crap, although they could have at
    > least supplied something that writes to the serial port.


    68HC16s don't know anything about serial ports, so why would
    they bother?

    You should write your data to a buffer with sprintf or some other
    method, and then send that buffer to the serial port, using a
    function specifically designed for writing to serial ports.

    > I noticed from looking around that putchar returns EOF if unsuccessful. EOF
    > is defined as -1 in the compiler header file. Therefore, it occurs to me
    > that putchar can only be used for ASCII data. This is OK, I just need to
    > make sure I have that right. Because, binary data could include -1 right?
    > That means I should never use it alone to send binary data. If so, is this
    > true for the PC? After all, it's counterpart, getchar retrives binary scan
    > codes from the keyboard unless they have already been converted to ASCII
    > characters before they get to that level.


    getchar and putchar work with unsigned values (ie. the range 0-255,
    if you have 8-bit chars). You should cast signed chars to unsigned
    before passing them to 'putchar', eg:

    char *p, *str = "héllo";
    for (p = str; *p; ++p)
    putchar( (unsigned char) *p );


    > As an embedded programmer, I am not real familiar with what normal pass/fail
    > return codes should be.


    Use your serial port functions, rather than trying to muck around
    with someone else's standard library. Who knows, the next version of
    your compiler might change something internally that will render
    your customised putchar useless.

    > The high level languages were developed around full OS systems
    > (Unix etc.) and then seem to have migrated to the embedded world
    > leaving some us without familiarity of conventions.


    Embedded compilers try to comply with the C standard for
    freestanding implementations. Read it, if you have a few spare hours.
    Old Wolf, Jul 9, 2005
    #6
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. John den Haan

    disable putchar line-wrapping?

    John den Haan, Feb 18, 2007, in forum: C Programming
    Replies:
    7
    Views:
    364
    Gordon Burditt
    Feb 19, 2007
  2. Replies:
    9
    Views:
    567
    SM Ryan
    Oct 20, 2007
  3. c gordon liddy

    || putchar(ch == '\177' ? '?' : ch | 0100) == EOF)

    c gordon liddy, Mar 28, 2008, in forum: C Programming
    Replies:
    8
    Views:
    409
    David Thompson
    Apr 7, 2008
  4. gervaz

    putchar(8)

    gervaz, Oct 16, 2009, in forum: Python
    Replies:
    0
    Views:
    349
    gervaz
    Oct 16, 2009
  5. gervaz

    putchar(8)

    gervaz, Oct 16, 2009, in forum: Python
    Replies:
    4
    Views:
    1,899
    Dave Angel
    Oct 17, 2009
Loading...

Share This Page