?login_element?

Subversion Repositories NedoOS

Rev

Blame | Last modification | View Log | Download | RSS feed

  1. /*-------------------------------------------------------------------------
  2.    _memset.c - part of string library functions
  3.  
  4.    Copyright (C) 1999, Sandeep Dutta . sandeep.dutta@usa.net
  5.    mcs51 assembler by Frieder Ferlemann (2007)
  6.  
  7.    This library is free software; you can redistribute it and/or modify it
  8.    under the terms of the GNU General Public License as published by the
  9.    Free Software Foundation; either version 2, or (at your option) any
  10.    later version.
  11.  
  12.    This library is distributed in the hope that it will be useful,
  13.    but WITHOUT ANY WARRANTY; without even the implied warranty of
  14.    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15.    GNU General Public License for more details.
  16.  
  17.    You should have received a copy of the GNU General Public License
  18.    along with this library; see the file COPYING. If not, write to the
  19.    Free Software Foundation, 51 Franklin Street, Fifth Floor, Boston,
  20.    MA 02110-1301, USA.
  21.  
  22.    As a special exception, if you link this library with other files,
  23.    some of which are compiled with SDCC, to produce an executable,
  24.    this library does not by itself cause the resulting executable to
  25.    be covered by the GNU General Public License. This exception does
  26.    not however invalidate any other reasons why the executable file
  27.    might be covered by the GNU General Public License.
  28. -------------------------------------------------------------------------*/
  29.  
  30. #include <string.h>
  31.  
  32. #undef memset /* Avoid conflict with builtin memset() in Z80 and some related ports */
  33.  
  34. #if defined (_SDCC_NO_ASM_LIB_FUNCS) || !defined (__SDCC_mcs51) || \
  35.     (!defined (__SDCC_MODEL_SMALL) && !defined (__SDCC_MODEL_LARGE)) || \
  36.      (defined (__SDCC_STACK_AUTO) || defined (__SDCC_PARMS_IN_BANK1) )
  37.  
  38. #ifdef __SDCC_BROKEN_STRING_FUNCTIONS
  39. void *memset (void *s, unsigned char c, size_t n)
  40. #else
  41. void *memset (void *s, int c, size_t n)
  42. #endif
  43. {
  44.  register unsigned char *ret = s;
  45.  
  46.  while (n--)
  47.    {
  48.       *(unsigned char *) ret = c;
  49.       ret = ((unsigned char *) ret) + 1;
  50.    }
  51.  
  52.    return s;
  53. }
  54.  
  55. #else
  56.  
  57.   /* assembler implementation for mcs51 */
  58.   static void dummy(void) __naked
  59.   {
  60.     __asm
  61.  
  62.   /* assigning function parameters to registers.
  63.      __SDCC_PARMS_IN_BANK1 or __SDCC_STACK_AUTO not yet implemented. */
  64.   #if defined (__SDCC_MODEL_SMALL)
  65.  
  66.     #if defined(__SDCC_NOOVERLAY)
  67.         .area DSEG    (DATA)
  68.     #else
  69.         .area OSEG    (OVR,DATA)
  70.     #endif
  71.         _memset_PARM_2::
  72.               .ds 1
  73.         _memset_PARM_3::
  74.               .ds 2
  75.  
  76.         .area CSEG    (CODE)
  77.  
  78.         _memset::
  79.  
  80.         ;   Assign buf (b holds memspace, no need to touch)
  81.                 mov     r4,dpl
  82.                 mov     r5,dph
  83.                 ;
  84.         ;   Assign count
  85.                 mov     r6,_memset_PARM_3
  86.                 mov     r7,(_memset_PARM_3 + 1)
  87.                 ;
  88.         ;   if (!count) return buf;
  89.         ;   check for count != 0 intermangled with gymnastic
  90.         ;   preparing djnz instructions
  91.                 cjne    r6,#0x00,COUNT_LSB_NOT_ZERO
  92.                 mov     a,r7
  93.                 jz      MEMSET_END
  94.                 dec     r7
  95.         COUNT_LSB_NOT_ZERO:
  96.                 inc     r7
  97.                 ;
  98.                 ; This was 8 byte overhead for preparing
  99.                 ; the count argument for an integer loop with two
  100.                 ; djnz instructions - it might make sense to
  101.                 ; let SDCC automatically generate this when
  102.                 ; it encounters a loop like:
  103.                 ; for(i=0;i<j;i++){...}
  104.                 ; (at least for option --opt-code-speed)
  105.                 ;
  106.  
  107.         ;   Assign ch
  108.                 mov     a,_memset_PARM_2
  109.  
  110.   #else
  111.  
  112.         .area XSEG    (XDATA)
  113.  
  114.         _memset_PARM_2::
  115.                 .ds 1
  116.         _memset_PARM_3::
  117.                 .ds 2
  118.  
  119.         .area CSEG    (CODE)
  120.  
  121.         _memset::
  122.  
  123.         ;   Assign buf (b holds memspace, no need to touch)
  124.                 mov     r4,dpl
  125.                 mov     r5,dph
  126.                 ;
  127.         ;   Assign count
  128.                 mov     dptr,#_memset_PARM_3
  129.                 movx    a,@dptr
  130.                 mov     r6,a
  131.                 inc     dptr
  132.                 movx    a,@dptr
  133.                 mov     r7,a
  134.                 ;
  135.         ;   if (!count) return buf;
  136.         ;   check for count != 0 intermangled with gymnastic
  137.         ;   preparing djnz instructions
  138.                 cjne    r6,#0x00,COUNT_LSB_NOT_ZERO
  139.         ;   acc holds r7
  140.                 jz      MEMSET_END
  141.                 dec     r7
  142.         COUNT_LSB_NOT_ZERO:
  143.                 inc     r7
  144.                 ;
  145.         ;   Assign ch
  146.                 mov     dptr,#_memset_PARM_2
  147.                 movx    a,@dptr
  148.         ;   acc is precious now
  149.                 ;
  150.         ;   Restore dptr
  151.                 mov     dpl,r4
  152.                 mov     dph,r5
  153.  
  154.   #endif
  155.  
  156.         /* now independent of the parameter passing everything
  157.            should be in registers by now and the loop may start */
  158.         ;   _memset.c do {
  159.  
  160.         MEMSET_LOOP:
  161.         ;   _memset.c *p = ch;
  162.                 lcall   __gptrput
  163.  
  164.         ;   _memset.c p++;
  165.                 inc     dptr
  166.  
  167.         ;   _memset.c } while(--count) ;
  168.                 djnz    r6,MEMSET_LOOP
  169.                 djnz    r7,MEMSET_LOOP
  170.                 ;
  171.  
  172.         MEMSET_END:
  173.         ;   _memset.c return buf ;
  174.                 ; b was unchanged
  175.                 mov     dpl,r4
  176.                 mov     dph,r5
  177.                 ;
  178.                 ret
  179.  
  180.     __endasm;
  181.   }
  182.  
  183. #endif
  184.