This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

System_printf + SysStd + rts6000 is not thread-safe

Hi,

Reviewing System module implementation I noticed that System_printf() does not enter the System gate and calls system support proxy putch() method which is implemented in SysStd as a direct call to the RTS's putchar() function. In rts6000 putchar() calls fputc() which does not use _lock() and, as I understand it, is not thread-safe by design.

Have I missed something?

Cheers,

Dmitry

XDC 3.23.04.60/3.24.07.73

rts6000 from CCS 5.0/5.2 (I haven't looked at ccs5.4 yet)

  • Hi Dmitry,

    Can you check which setting you have for 'C Standard Library Lock' in your BIOS config file (*.cfg)?

    I believe SysStd is only as thread safe as the underlying RTS library/APIs that it uses.

    Please see this post for some good details on all of this.

    Steve

  • Steve,

    I know about rtsGateType (we use GateSwi in our cfg). The problem is that RTS seems to not calling _lock() in putchar() and associated calls.

    Take a look at the following excerpts from fputc.c and stdio.h:

    _CODE_ACCESS int putchar(int _x) { return(_putchar(_x)); }

    #define _putchar(_x)    putc((_x), stdout)

    _CODE_ACCESS int putc(int _x, FILE *_fp) { return(fputc(_x, _fp)); }

    _CODE_ACCESS int fputc(int _c, register FILE *_fp)
    {
       /*------------------------------------------------------------------------*/
       /* Make sure that the stream is writeable.                                */
       /*------------------------------------------------------------------------*/
       if(! _wrt_ok(_fp)) return EOF;

       /*------------------------------------------------------------------------*/
       /* If the stream is non-buffered, call the lowlevel WRITE function.       */
       /*------------------------------------------------------------------------*/
       if(_BUFFMODE(_fp) == _IONBF)
       {
          char cbuf = (char)_c;

          if((write(_fp->fd, &cbuf, 1)) == -1)
          {
             _SET(_fp, _STATERR);
             return (EOF);
          }
          else return ((unsigned char)_c);
       }

       /*------------------------------------------------------------------------*/
       /* Check for room in the buffer. If room, add the character. Must         */
       /* check before writing because C++ library fills the buffer to           */
       /* capacity, then calls fputc() from overflow() (CQXXXXX).                */
       /*------------------------------------------------------------------------*/
       if ((_fp->pos >= _fp->bufend) && _doflush(_fp))
       {
          _SET(_fp, _STATERR);
          return (EOF);
       }

       *(_fp->pos++) = (unsigned char)_c;
       /*------------------------------------------------------------------------*/
       /* If a line-buffered stream reached a newline character, flush it.       */
       /*------------------------------------------------------------------------*/
       if ((_STCHK(_fp, _IOLBF) && _c == '\n') && _doflush(_fp))
       {
          _SET(_fp, _STATERR);
          return (EOF);
       }

       return((unsigned char)_c);
    }

    Regards,

    Dmitry

  • The RTS support library supplied with C6000 compiler release version 7.4.x is thread-safe.  Here is a excerpt from the readme about it ...

    To help ensure thread-safety of an OpenMP application, a thread-safe version
    of the Run Time Support (RTS) library should also be used during the link
    step. The 7.4.0 Code Generation Tools package provides thread-safe RTS
    libraries for this purpose.

    Please see this wiki article for how to update the compiler.

    Thanks and regards,

    -George