Ticket #1729: smp-Patch.diff

File smp-Patch.diff, 63.6 KB (added by Jennifer Averett, on 01/07/11 at 18:09:30)

Patch to add SMP single core support. This should be used in conjunction with the tar ball that has the added smp directories.

  • c/src/lib/libbsp/i386/i386ex/Makefile.am

    ? c/src/lib/libbsp/i386/shared/smp
    ? c/src/lib/libbsp/i386/shared/irq/hold
    ? c/src/lib/libbsp/shared/smp
    ? c/src/lib/libbsp/sparc/leon3/smp
    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/i386ex/Makefile.am,v
    retrieving revision 1.46
    diff -u -r1.46 Makefile.am
     
    6363# timer
    6464libbsp_a_SOURCES += timer/timer.c timer/timerisr.S
    6565
     66if HAS_SMP
     67libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     68endif
     69
    6670if HAS_NETWORKING
    6771network_CPPFLAGS = -D__INSIDE_RTEMS_BSD_TCPIP_STACK__ -D_KERNEL
    6872noinst_PROGRAMS += network.rel
  • c/src/lib/libbsp/i386/i386ex/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/i386ex/configure.ac,v
    retrieving revision 1.26
    diff -u -r1.26 configure.ac
     
    1616RTEMS_PROG_CCAS
    1717
    1818RTEMS_CHECK_NETWORKING
     19RTEMS_CHECK_SMP
     20
     21AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     22AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
    1923
    2024## if this is an i386, does gas have good code16 support?
    2125RTEMS_I386_GAS_CODE16
    2226AM_CONDITIONAL(RTEMS_GAS_CODE16,test "$RTEMS_GAS_CODE16" = "yes")
    2327
    24 AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
    25 
    2628RTEMS_BSP_CLEANUP_OPTIONS(0, 0)
    2729
    2830# Explicitly list all Makefiles here
  • c/src/lib/libbsp/i386/pc386/Makefile.am

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/pc386/Makefile.am,v
    retrieving revision 1.56
    diff -u -r1.56 Makefile.am
     
    108108# ide
    109109libbsp_a_SOURCES += ide/idecfg.c ide/ide.c
    110110
     111if HAS_SMP
     112libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     113endif
     114
    111115if HAS_NETWORKING
    112116ne2000_CPPFLAGS = -D__INSIDE_RTEMS_BSD_TCPIP_STACK__
    113117noinst_PROGRAMS += ne2000.rel
  • c/src/lib/libbsp/i386/pc386/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/pc386/configure.ac,v
    retrieving revision 1.38
    diff -u -r1.38 configure.ac
     
    1717RTEMS_PROG_CCAS
    1818
    1919RTEMS_CHECK_NETWORKING
     20RTEMS_CHECK_SMP
    2021
    2122RTEMS_BSPOPTS_SET([USE_COM1_AS_CONSOLE],[*],[0])
    2223RTEMS_BSPOPTS_HELP([USE_COM1_AS_CONSOLE],
     
    6263   from Intel and AMD will maintain a constant-rate TSC regardless.
    6364])
    6465
     66#define CLOCK_DRIVER_USE_8254 $CLOCK_DRIVER_USE_8254
    6567RTEMS_BSPOPTS_SET([CLOCK_DRIVER_USE_8254],[*],[0])
    6668RTEMS_BSPOPTS_HELP([CLOCK_DRIVER_USE_8254],
    6769[If enabled, the clock driver will use the good old 8254 chip
     
    7880  AC_MSG_ERROR([pc386 both TSC and 8254 specified for clock driver])
    7981fi
    8082
    81 #define CLOCK_DRIVER_USE_8254 $CLOCK_DRIVER_USE_8254
     83RTEMS_BSPOPTS_SET([BSP_HAS_SMP],[*],[1])
     84RTEMS_BSPOPTS_HELP([BSP_HAS_SMP],
     85[Always defined when on a pc386 to enable the pc386 support for
     86 determining the CPU core number in an SMP configuration.])
     87
    8288## if this is an i386, does gas have good code16 support?
    8389RTEMS_I386_GAS_CODE16
    8490AM_CONDITIONAL(RTEMS_GAS_CODE16,[test "$RTEMS_GAS_CODE16" = "yes"])
    8591
    86 AM_CONDITIONAL(HAS_NETWORKING,[test "$HAS_NETWORKING" = "yes"])
     92
     93AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     94AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
     95
    8796
    8897AC_SUBST([RTEMS_ROOT],[${rtems_updir}'$(top_builddir)'])
    8998
  • c/src/lib/libbsp/i386/pc386/startup/ldsegs.S

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/pc386/startup/ldsegs.S,v
    retrieving revision 1.19
    diff -u -r1.19 ldsegs.S
     
    2424|   ldsegs.s,v 1.4 1996/04/20 16:48:30 joel Exp - go32 BSP
    2525| With the following copyright notice:
    2626| **************************************************************************
    27 | *  COPYRIGHT (c) 1989-1999.
     27| *  COPYRIGHT (c) 1989-2011.
    2828| *  On-Line Applications Research Corporation (OAR).
    2929| *
    3030| *  The license and distribution terms for this file may be
     
    9696SYM (_load_segments):
    9797
    9898        lgdt SYM(gdtdesc)
    99         lidt SYM(idtdesc)
     99        lidt SYM(IDT_Descriptor)
    100100
    101101        /* Load CS, flush prefetched queue */
    102102        ljmp $0x8, $next_step
     
    211211+--------------------------------------------------------------------------*/
    212212
    213213        .p2align 4
    214 SYM(idtdesc):
     214        PUBLIC(IDT_Descriptor)
     215SYM(IDT_Descriptor):
    215216        .word  (256*8 - 1)
    216217        .long  SYM (Interrupt_descriptor_table)
    217218
  • c/src/lib/libbsp/i386/shared/irq/irq_asm.S

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/shared/irq/irq_asm.S,v
    retrieving revision 1.20
    diff -u -r1.20 irq_asm.S
     
    44 *
    55 *  Copyright (C) 1998 valette@crf.canon.fr
    66 *
     7 *  COPYRIGHT (c) 1989-2011.
     8 *  On-Line Applications Research Corporation (OAR).
     9 *
    710 *  The license and distribution terms for this file may be
    8  *  found in found in the file LICENSE in this distribution or at
     11 *  found in the file LICENSE in this distribution or at
    912 *  http://www.rtems.com/license/LICENSE.
    1013 *
    1114 *  $Id: irq_asm.S,v 1.20 2011/01/06 14:34:08 joel Exp $
    1215 */
    1316
    1417#include <rtems/asm.h>
     18#include <rtems/system.h>
    1519#include <bspopts.h>
    1620#include <bsp/irq_asm.h>
    1721#include <rtems/score/cpu.h>
     
    140144ISR_STOP:
    141145.check_stack_switch:
    142146        movl      esp, ebp                  /* ebp = previous stack pointer */
    143 
    144         movl      $SYM(_Per_CPU_Information), ebx
     147#if defined(RTEMS_SMP) && defined(BSP_HAS_SMP)
     148        movl     SYM(_Per_CPU_Information_p), ebx
     149        call     SYM(rtems_bsp_smp_get_current)
     150        mov      (ebx,eax,4), ebx
     151#else
     152        movl     $SYM(_Per_CPU_Information), ebx
     153#endif
    145154
    146155        /* is this the outermost interrupt? */
    147156        cmpl      $0, PER_CPU_ISR_NEST_LEVEL(ebx)
  • c/src/lib/libbsp/i386/ts_386ex/Makefile.am

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/ts_386ex/Makefile.am,v
    retrieving revision 1.43
    diff -u -r1.43 Makefile.am
     
    6767# timer
    6868libbsp_a_SOURCES += timer/timer.c timer/timerisr.S
    6969
     70if HAS_SMP
     71libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     72endif
     73
    7074if HAS_NETWORKING
    7175include_HEADERS += include/wd80x3.h
    7276
  • c/src/lib/libbsp/i386/ts_386ex/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/i386/ts_386ex/configure.ac,v
    retrieving revision 1.27
    diff -u -r1.27 configure.ac
     
    1616RTEMS_PROG_CCAS
    1717
    1818RTEMS_CHECK_NETWORKING
     19RTEMS_CHECK_SMP
     20
     21AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     22AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
    1923
    2024## if this is an i386, does gas have good code16 support?
    2125RTEMS_I386_GAS_CODE16
    2226AM_CONDITIONAL(RTEMS_GAS_CODE16,test "$RTEMS_GAS_CODE16" = "yes")
    2327
    24 AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
    25 
    2628RTEMS_CONFIG_BUILD_SUBDIRS(tools)
    2729
    2830# bsp-specific options
  • c/src/lib/libbsp/sparc/erc32/Makefile.am

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/erc32/Makefile.am,v
    retrieving revision 1.52
    diff -u -r1.52 Makefile.am
     
    4040    ../../shared/bspstart.c ../../shared/bootcard.c ../../shared/bspinit.c \
    4141    ../../shared/sbrk.c startup/setvec.c startup/spurious.c \
    4242    startup/erc32mec.c startup/boardinit.S startup/bspidle.c
     43# ISR Handler
     44libbsp_a_SOURCES += ../../sparc/shared/irq_asm.S
    4345# gnatsupp
    4446libbsp_a_SOURCES += gnatsupp/gnatsupp.c ../../sparc/shared/gnatcommon.c
    4547# console
     
    5153# timer
    5254libbsp_a_SOURCES += timer/timer.c
    5355
     56if HAS_SMP
     57libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     58endif
     59
    5460if HAS_NETWORKING
    5561erc32sonic_CPPFLAGS = -D__INSIDE_RTEMS_BSD_TCPIP_STACK__
    5662noinst_PROGRAMS += erc32sonic.rel
  • c/src/lib/libbsp/sparc/erc32/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/erc32/configure.ac,v
    retrieving revision 1.29
    diff -u -r1.29 configure.ac
     
    1616RTEMS_PROG_CCAS
    1717
    1818RTEMS_CHECK_NETWORKING
     19RTEMS_CHECK_SMP
    1920
    2021AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     22AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
     23
     24## This is needed to generate the field offsets of the per CPU
     25## data structure so they can be accessed from assembly code.
     26AC_CHECK_SIZEOF([void *])
    2127
    2228RTEMS_CONFIG_BUILD_SUBDIRS(tools)
    2329
  • c/src/lib/libbsp/sparc/leon2/Makefile.am

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/leon2/Makefile.am,v
    retrieving revision 1.25
    diff -u -r1.25 Makefile.am
     
    6060    ../../sparc/shared/bspgetworkarea.c ../../shared/bootcard.c \
    6161    ../../shared/sbrk.c startup/setvec.c startup/spurious.c startup/bspidle.c \
    6262    ../../shared/bspinit.c
     63# ISR Handler
     64libbsp_a_SOURCES += ../../sparc/shared/irq_asm.S
    6365# gnatsupp
    6466libbsp_a_SOURCES += gnatsupp/gnatsupp.c ../../sparc/shared/gnatcommon.c
    6567# console
     
    9799# timer
    98100libbsp_a_SOURCES += timer/timer.c
    99101
     102if HAS_SMP
     103libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     104endif
     105
    100106if HAS_NETWORKING
    101107noinst_PROGRAMS += leon_smc91111.rel
    102108leon_smc91111_rel_SOURCES = leon_smc91111/leon_smc91111.c
  • c/src/lib/libbsp/sparc/leon2/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/leon2/configure.ac,v
    retrieving revision 1.16
    diff -u -r1.16 configure.ac
     
    1616RTEMS_PROG_CCAS
    1717
    1818RTEMS_CHECK_NETWORKING
     19RTEMS_CHECK_SMP
    1920
    2021AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     22AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
     23
     24## This is needed to generate the field offsets of the per CPU
     25## data structure so they can be accessed from assembly code.
     26AC_CHECK_SIZEOF([void *])
    2127
    2228RTEMS_CONFIG_BUILD_SUBDIRS(tools)
    2329
  • c/src/lib/libbsp/sparc/leon3/Makefile.am

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/leon3/Makefile.am,v
    retrieving revision 1.29
    diff -u -r1.29 Makefile.am
     
    4343    ../../sparc/shared/bspgetworkarea.c ../../shared/sbrk.c startup/setvec.c \
    4444    startup/spurious.c startup/bspidle.S \
    4545    ../../shared/bspinit.c
     46# ISR Handler
     47libbsp_a_SOURCES += ../../sparc/shared/irq_asm.S
    4648# gnatsupp
    4749libbsp_a_SOURCES += gnatsupp/gnatsupp.c ../../sparc/shared/gnatcommon.c
    4850# amba
     
    9092# timer
    9193libbsp_a_SOURCES += timer/timer.c
    9294
     95if HAS_SMP
     96libbsp_a_SOURCES += ../../shared/smp/getcpuid.c ../../shared/smp/smp_stub.c
     97endif
     98
    9399if HAS_NETWORKING
    94100noinst_PROGRAMS += leon_smc91111.rel
    95101leon_smc91111_rel_SOURCES = leon_smc91111/leon_smc91111.c
  • c/src/lib/libbsp/sparc/leon3/configure.ac

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/leon3/configure.ac,v
    retrieving revision 1.16
    diff -u -r1.16 configure.ac
     
    1616RTEMS_PROG_CCAS
    1717
    1818RTEMS_CHECK_NETWORKING
     19RTEMS_CHECK_SMP
    1920
    2021AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
     22AM_CONDITIONAL(HAS_SMP,[test "$rtems_cv_HAS_SMP" = "yes"])
     23
     24## This is needed to generate the field offsets of the per CPU
     25## data structure so they can be accessed from assembly code.
     26AC_CHECK_SIZEOF([void *])
    2127
    2228RTEMS_CONFIG_BUILD_SUBDIRS(tools)
    2329
     
    3743 time spent in the idle task is minimized.  This significantly reduces
    3844 the wall time required to execute the RTEMS test suites.])
    3945
     46RTEMS_BSPOPTS_SET([BSP_LEON3_SMP],[*],[1])
     47RTEMS_BSPOPTS_HELP([BSP_LEON3_SMP],
     48[Always defined when on a LEON3 to enable the LEON3 support for
     49 determining the CPU core number in an SMP configuration.])
     50
    4051RTEMS_BSP_CLEANUP_OPTIONS(0, 0)
    4152
    4253# Explicitly list all Makefiles here
  • c/src/lib/libbsp/sparc/shared/start.S

    RCS file: /usr1/CVS/rtems/c/src/lib/libbsp/sparc/shared/start.S,v
    retrieving revision 1.16
    diff -u -r1.16 start.S
     
    77 *  distribution of the SPARC Instruction Simulator (SIS) found
    88 *  at ftp://ftp.estec.esa.nl/pub/ws/wsd/erc32.
    99 *
    10  *  COPYRIGHT (c) 1989-2006.
     10 *  COPYRIGHT (c) 1989-2011.
    1111 *  On-Line Applications Research Corporation (OAR).
    1212 *
    1313 *  The license and distribution terms for this file may be
     
    1818 */
    1919
    2020#include <rtems/asm.h>
     21#include <rtems/system.h>
    2122#include <bspopts.h>
    2223
     24#if defined(RTEMS_SMP) && BSP_LEON3_SMP
     25#define ENABLE_SMP
     26#endif
     27
    2328/*
    2429 *  Unexpected trap will halt the processor by forcing it to error state
    2530 */
     
    221226        nop
    222227        nop
    223228
     229#if defined(ENABLE_SMP)
     230        rd      %asr17, %g1
     231        srl     %g1, 28, %g1
     232        and     %g1, 0xff, %g1                  ! extract cpu id
     233        cmp     %g1, 0
     234        beq     cpu0
     235        nop
     236        set     SYM(bsp_ap_stack), %g1          ! set the stack pointer
     237        ld      [%g1], %sp
     238        mov     %sp, %fp
     239        nop
     240        set     SYM(bsp_ap_entry), %g1          ! where to start
     241        ld      [%g1], %g1
     242        call    %g1
     243        nop
     244cpu0:
     245#endif
     246
    224247        set     (SYM(rdb_start)), %g6   ! End of RAM
    225248        st      %sp, [%g6]
    226249        sub     %sp, 4, %sp             ! stack starts at end of RAM - 4
     
    340363        ta      0                       ! Halt if _main returns ...
    341364        nop
    342365
     366#if defined(ENABLE_SMP)
     367        .common bsp_ap_stack, 4, 4
     368        .common bsp_ap_entry, 4, 4
     369#endif
     370
     371
    343372/* end of file */
  • cpukit/configure.ac

    RCS file: /usr1/CVS/rtems/cpukit/configure.ac,v
    retrieving revision 1.196
    diff -u -r1.196 configure.ac
     
    141141  RTEMS_CHECK_MULTIPROCESSING
    142142RTEMS_CHECK_POSIX_API
    143143RTEMS_CHECK_NETWORKING
     144RTEMS_CHECK_SMP
    144145
    145146rtems_major=`echo _RTEMS_VERSION | sed "s/\..*//"`
    146147rtems_minor=`echo _RTEMS_VERSION | sed "s/[[0-9]][[0-9]]*\.//;s/\..*//"`
     
    172173  [1],
    173174  [if posix api is supported])
    174175
     176RTEMS_CPUOPT([RTEMS_SMP],
     177  [test x"$RTEMS_HAS_SMP" = xyes],
     178  [1],
     179  [if SMP is enabled])
     180
    175181RTEMS_CPUOPT([RTEMS_NETWORKING],
    176182  [test x"$rtems_cv_HAS_NETWORKING" = xyes],
    177183  [1],
     
    296302AM_CONDITIONAL(NEWLIB,test x"$RTEMS_USE_NEWLIB" = x"yes")
    297303
    298304AM_CONDITIONAL(HAS_MP,test x"$enable_multiprocessing" = x"yes" )
     305AM_CONDITIONAL(HAS_SMP,[test "$RTEMS_HAS_SMP" = "yes"])
    299306
    300307AM_CONDITIONAL(HAS_PTHREADS,test x"$rtems_cv_HAS_POSIX_API" = x"yes")
    301308AM_CONDITIONAL(LIBNETWORKING,test x"$rtems_cv_HAS_NETWORKING" = x"yes")
  • cpukit/sapi/include/confdefs.h

    RCS file: /usr1/CVS/rtems/cpukit/sapi/include/confdefs.h,v
    retrieving revision 1.153
    diff -u -r1.153 confdefs.h
     
    2626 */
    2727
    2828/*
    29  *  COPYRIGHT (c) 1989-2010.
     29 *  COPYRIGHT (c) 1989-2011.
    3030 *  On-Line Applications Research Corporation (OAR).
    3131 *
    3232 *  The license and distribution terms for this file may be
     
    174174  extern int rtems_telnetd_maximum_ptys;
    175175#endif
    176176
     177#if defined(RTEMS_SMP)
     178  /*
     179   *  If configured for SMP, then we need to know the maximum CPU cores.
     180   */
     181  #if !defined(CONFIGURE_SMP_APP)
     182    #if !defined(CONFIGURE_SMP_CPUS)
     183      #define CONFIGURE_SMP_CPUS 1
     184    #endif
     185  #else
     186    #if !defined(CONFIGURE_SMP_CPUS)
     187      #error "CONFIGURE_SMP_CPUS not specified for SMP Application"
     188    #endif
     189  #endif
     190#endif
     191
    177192/*
    178193 *  Filesystems and Mount Table Configuration.
    179194 *
     
    18361851  _Configure_Object_RAM(1, sizeof(API_Mutex_Control))
    18371852
    18381853/**
    1839  *  This defines the amount of memory reserved for the IDLE task
    1840  *  control structures and stack.
     1854 *  This defines the formula used to compute the amount of memory
     1855 *  reserved for IDLE task control structures and stacks.
     1856 */
     1857#define CONFIGURE_IDLE_TASKS(_count) \
     1858    (CONFIGURE_MEMORY_FOR_TASKS(_count, 0) + \
     1859      _count * _Configure_From_workspace( \
     1860       (CONFIGURE_IDLE_TASK_STACK_SIZE - CONFIGURE_MINIMUM_TASK_STACK_SIZE)))
     1861
     1862/**
     1863 *  This calculates the amount of memory reserved for the IDLE tasks.
     1864 *  In an SMP system, each CPU core has its own idle task.
    18411865 */
    1842 #define CONFIGURE_MEMORY_FOR_IDLE_TASK \
    1843     (CONFIGURE_MEMORY_FOR_TASKS(1, 0) + \
    1844      (CONFIGURE_IDLE_TASK_STACK_SIZE - CONFIGURE_MINIMUM_TASK_STACK_SIZE))
     1866#if defined(RTEMS_SMP)
     1867  #define CONFIGURE_MEMORY_FOR_IDLE_TASK \
     1868          CONFIGURE_IDLE_TASKS(CONFIGURE_SMP_CPUS)
     1869#else
     1870  #define CONFIGURE_MEMORY_FOR_IDLE_TASK \
     1871          CONFIGURE_IDLE_TASKS(1)
     1872#endif
    18451873
    18461874/**
    18471875 *  This macro accounts for general RTEMS system overhead.
     
    19291957   CONFIGURE_MEMORY_FOR_USER_EXTENSIONS(CONFIGURE_MAXIMUM_USER_EXTENSIONS) \
    19301958  )
    19311959
     1960#if defined(RTEMS_SMP)
     1961  #define CONFIGURE_MEMORY_FOR_SMP \
     1962     (_Configure_From_workspace( \
     1963         CONFIGURE_SMP_CPUS * sizeof(Per_CPU_Control)) + \
     1964      _Configure_From_workspace( \
     1965         CONFIGURE_SMP_CPUS * sizeof(Per_CPU_Control *)) + \
     1966      (CONFIGURE_SMP_CPUS * \
     1967        _Configure_From_workspace( CONFIGURE_INTERRUPT_STACK_SIZE )) \
     1968     )
     1969#else
     1970  #define CONFIGURE_MEMORY_FOR_SMP 0
     1971#endif
     1972
    19321973#if defined(CONFIGURE_CONFDEFS_DEBUG) && defined(CONFIGURE_INIT)
    19331974  /**
    19341975   *  This is a debug mechanism, so if you need to, the executable will
     
    20432084   CONFIGURE_MEMORY_FOR_CLASSIC + \
    20442085   CONFIGURE_MEMORY_FOR_POSIX + \
    20452086   (CONFIGURE_MAXIMUM_POSIX_THREADS * CONFIGURE_MINIMUM_TASK_STACK_SIZE ) + \
    2046    (CONFIGURE_MAXIMUM_GOROUTINES * CONFIGURE_MINIMUM_TASK_STACK_SIZE ) + \
     2087   (CONFIGURE_MAXIMUM_GOROUTINES * CONFIGURE_MINIMUM_TASK_STACK_SIZE) + \
    20472088   CONFIGURE_INITIALIZATION_THREADS_STACKS + \
    20482089   CONFIGURE_MEMORY_FOR_STATIC_EXTENSIONS + \
    20492090   CONFIGURE_MEMORY_FOR_MP + \
     2091   CONFIGURE_MEMORY_FOR_SMP + \
    20502092   CONFIGURE_MESSAGE_BUFFER_MEMORY + \
    20512093   (CONFIGURE_MEMORY_OVERHEAD * 1024) + \
    20522094   (CONFIGURE_EXTRA_TASK_STACKS) + (CONFIGURE_ADA_TASKS_STACK) \
     
    21492191
    21502192#endif /* CONFIGURE_HAS_OWN_CONFIGURATION_TABLE */
    21512193
     2194#if defined(RTEMS_SMP)
     2195  /*
     2196   *  Instantiate the variable which specifies the number of CPUs
     2197   *  in an SMP configuration.
     2198   */
     2199  #if defined(CONFIGURE_INIT)
     2200    uint32_t rtems_smp_maximum_cpus = CONFIGURE_SMP_CPUS;
     2201  #else
     2202    extern uint32_t rtems_smp_maximum_cpus;
     2203  #endif
     2204#endif
     2205
    21522206/*
    21532207 *  If the user has configured a set of Classic API Initialization Tasks,
    21542208 *  then we need to install the code that runs that loop.
  • cpukit/sapi/src/exinit.c

    RCS file: /usr1/CVS/rtems/cpukit/sapi/src/exinit.c,v
    retrieving revision 1.56
    diff -u -r1.56 exinit.c
     
    11/*
    22 *  Initialization Manager
    33 *
    4  *  COPYRIGHT (c) 1989-2008.
     4 *  COPYRIGHT (c) 1989-2011.
    55 *  On-Line Applications Research Corporation (OAR).
    66 *
    77 *  The license and distribution terms for this file may be
     
    5757  #include <rtems/posix/posixapi.h>
    5858#endif
    5959
     60#if defined(RTEMS_SMP)
     61  #include <rtems/bspsmp.h>
     62#endif
     63
    6064Objects_Information *_Internal_Objects[ OBJECTS_INTERNAL_CLASSES_LAST + 1 ];
    6165
    6266void rtems_initialize_data_structures(void)
     
    114118   */
    115119  _Workspace_Handler_initialization();
    116120
     121  #if defined(RTEMS_SMP)
     122    per_cpu_initialize();
     123  #endif
     124
    117125  _User_extensions_Handler_initialization();
    118126  _ISR_Handler_initialization();
    119127
     
    150158    _POSIX_API_Initialize();
    151159  #endif
    152160
     161  /*
     162   * Discover and initialize the secondary cores in an SMP system.
     163   */
     164  #if defined(RTEMS_SMP)
     165    rtems_smp_number_of_cpus = rtems_bsp_smp_initialize(rtems_smp_maximum_cpus);
     166  #endif
     167
    153168  _System_state_Set( SYSTEM_STATE_BEFORE_MULTITASKING );
    154169
    155170  /*
  • cpukit/score/Makefile.am

    RCS file: /usr1/CVS/rtems/cpukit/score/Makefile.am,v
    retrieving revision 1.90
    diff -u -r1.90 Makefile.am
     
    1212include_rtemsdir = $(includedir)/rtems
    1313
    1414include_rtems_HEADERS = include/rtems/debug.h include/rtems/system.h \
    15     include/rtems/seterr.h
     15    include/rtems/seterr.h include/rtems/bspsmp.h
    1616
    1717include_rtems_scoredir = $(includedir)/rtems/score
    1818
     
    3434    include/rtems/score/timestamp64.h include/rtems/score/tod.h \
    3535    include/rtems/score/tqdata.h include/rtems/score/userext.h \
    3636    include/rtems/score/watchdog.h include/rtems/score/wkspace.h \
    37     include/rtems/score/cpuopts.h include/rtems/score/basedefs.h
     37    include/rtems/score/cpuopts.h include/rtems/score/basedefs.h \
     38    include/rtems/score/lock.h
    3839
    3940if HAS_PTHREADS
    4041include_rtems_score_HEADERS += include/rtems/score/corespinlock.h \
     
    8687libscore_a_SOURCES += src/mpci.c src/objectmp.c src/threadmp.c
    8788endif
    8889
     90libscore_a_SOURCES += src/smp.c src/lock.c
     91
    8992## CORE_APIMUTEX_C_FILES
    9093libscore_a_SOURCES += src/apimutex.c src/apimutexallocate.c \
    9194    src/apimutexlock.c src/apimutexunlock.c
  • cpukit/score/preinstall.am

    RCS file: /usr1/CVS/rtems/cpukit/score/preinstall.am,v
    retrieving revision 1.25
    diff -u -r1.25 preinstall.am
     
    3030        $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/seterr.h
    3131PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/seterr.h
    3232
     33$(PROJECT_INCLUDE)/rtems/bspsmp.h: include/rtems/bspsmp.h $(PROJECT_INCLUDE)/rtems/$(dirstamp)
     34        $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/bspsmp.h
     35PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/bspsmp.h
     36
    3337$(PROJECT_INCLUDE)/rtems/score/$(dirstamp):
    3438        @$(MKDIR_P) $(PROJECT_INCLUDE)/rtems/score
    3539        @: > $(PROJECT_INCLUDE)/rtems/score/$(dirstamp)
     
    183187        $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/basedefs.h
    184188PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/basedefs.h
    185189
     190$(PROJECT_INCLUDE)/rtems/score/lock.h: include/rtems/score/lock.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp)
     191        $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/lock.h
     192PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/lock.h
     193
    186194if HAS_PTHREADS
    187195$(PROJECT_INCLUDE)/rtems/score/corespinlock.h: include/rtems/score/corespinlock.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp)
    188196        $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/corespinlock.h
  • cpukit/score/cpu/i386/rtems/score/cpu.h

    RCS file: /usr1/CVS/rtems/cpukit/score/cpu/i386/rtems/score/cpu.h,v
    retrieving revision 1.36
    diff -u -r1.36 cpu.h
     
    66 *  This include file contains information pertaining to the Intel
    77 *  i386 processor.
    88 *
    9  *  COPYRIGHT (c) 1989-2008.
     9 *  COPYRIGHT (c) 1989-2011.
    1010 *  On-Line Applications Research Corporation (OAR).
    1111 *
    1212 *  The license and distribution terms for this file may be
     
    270270/* variables */
    271271
    272272SCORE_EXTERN Context_Control_fp  _CPU_Null_fp_context;
    273 SCORE_EXTERN void               *_CPU_Interrupt_stack_low;
    274 SCORE_EXTERN void               *_CPU_Interrupt_stack_high;
    275273
    276274#endif /* ASM */
    277275
     
    437435#define _CPU_Context_Restart_self( _the_context ) \
    438436   _CPU_Context_restore( (_the_context) );
    439437
     438#if defined(RTEMS_SMP)
     439  #define _CPU_Context_switch_to_first_task_smp( _the_context ) \
     440     _CPU_Context_restore( (_the_context) );
     441#endif
     442
    440443#define _CPU_Context_Fp_start( _base, _offset ) \
    441444   ( (void *) _Addresses_Add_offset( (_base), (_offset) ) )
    442445
  • cpukit/score/cpu/sparc/cpu_asm.S

    RCS file: /usr1/CVS/rtems/cpukit/score/cpu/sparc/cpu_asm.S,v
    retrieving revision 1.18
    diff -u -r1.18 cpu_asm.S
     
    44 *  in an specific CPU port of RTEMS.  These algorithms must be implemented
    55 *  in assembly language.
    66 *
    7  *  COPYRIGHT (c) 1989-2010.
     7 *  COPYRIGHT (c) 1989-2011.
    88 *  On-Line Applications Research Corporation (OAR).
    99 *
    1010 *  The license and distribution terms for this file may be
     
    319319 *
    320320 *  NOTE: It is unnecessary to reload some registers.
    321321 */
    322 
    323322        .align 4
    324323        PUBLIC(_CPU_Context_restore)
    325324SYM(_CPU_Context_restore):
     
    327326        rd      %psr, %o2
    328327        ba      SYM(_CPU_Context_restore_heir)
    329328        mov     %i0, %o1                      ! in the delay slot
     329        .align 4
    330330
     331#if defined(RTEMS_SMP)
    331332/*
    332  *  void _ISR_Handler()
    333  *
    334  *  This routine provides the RTEMS interrupt management.
    335  *
    336  *  We enter this handler from the 4 instructions in the trap table with
    337  *  the following registers assumed to be set as shown:
    338  *
    339  *    l0 = PSR
    340  *    l1 = PC
    341  *    l2 = nPC
    342  *    l3 = trap type
     333 *  void _CPU_Context_switch_to_first_task_smp(
     334 *    Context_Control *new_context
     335 *  )
    343336 *
    344  *  NOTE: By an executive defined convention, trap type is between 0 and 255 if
    345  *        it is an asynchonous trap and 256 and 511 if it is synchronous.
     337 *  This routine is only used to switch to the first task on a
     338 *  secondary core in an SMP configuration.  We do not need to
     339 *  flush all the windows and, in fact, this can be dangerous
     340 *  as they may or may not be initialized properly.  So we just
     341 *  reinitialize the PSR and WIM.
    346342 */
     343        PUBLIC(_CPU_Context_switch_to_first_task_smp)
     344SYM(_CPU_Context_switch_to_first_task_smp):
     345        save    %sp, -CPU_MINIMUM_STACK_FRAME_SIZE, %sp
    347346
    348         .align 4
    349         PUBLIC(_ISR_Handler)
    350 SYM(_ISR_Handler):
    351         /*
    352          *  Fix the return address for synchronous traps.
    353          */
    354 
    355         andcc   %l3, SPARC_SYNCHRONOUS_TRAP_BIT_MASK, %g0
    356                                       ! Is this a synchronous trap?
    357         be,a    win_ovflow            ! No, then skip the adjustment
    358         nop                           ! DELAY
    359         mov     %l1, %l6              ! save trapped pc for debug info
    360         mov     %l2, %l1              ! do not return to the instruction
    361         add     %l2, 4, %l2           ! indicated
    362 
    363 win_ovflow:
    364         /*
    365          *  Save the globals this block uses.
    366          *
    367          *  These registers are not restored from the locals.  Their contents
    368          *  are saved directly from the locals into the ISF below.
    369          */
    370 
    371         mov     %g4, %l4                 ! save the globals this block uses
    372         mov     %g5, %l5
    373 
    374         /*
    375          *  When at a "window overflow" trap, (wim == (1 << cwp)).
    376          *  If we get here like that, then process a window overflow.
    377          */
    378 
    379         rd      %wim, %g4
    380         srl     %g4, %l0, %g5            ! g5 = win >> cwp ; shift count and CWP
    381                                          !   are LS 5 bits ; how convenient :)
    382         cmp     %g5, 1                   ! Is this an invalid window?
    383         bne     dont_do_the_window       ! No, then skip all this stuff
    384         ! we are using the delay slot
    385 
    386         /*
    387          *  The following is same as a 1 position right rotate of WIM
    388          */
    389 
    390         srl     %g4, 1, %g5              ! g5 = WIM >> 1
    391         sll     %g4, SPARC_NUMBER_OF_REGISTER_WINDOWS-1 , %g4
    392                                          ! g4 = WIM << (Number Windows - 1)
    393         or      %g4, %g5, %g4            ! g4 = (WIM >> 1) |
    394                                          !      (WIM << (Number Windows - 1))
    395 
    396         /*
    397          *  At this point:
    398          *
    399          *    g4 = the new WIM
    400          *    g5 is free
    401          */
    402 
    403         /*
    404          *  Since we are tinkering with the register windows, we need to
    405          *  make sure that all the required information is in global registers.
    406          */
    407 
    408         save                          ! Save into the window
    409         wr      %g4, 0, %wim          ! WIM = new WIM
    410         nop                           ! delay slots
    411         nop
    412         nop
    413 
    414         /*
    415          *  Now save the window just as if we overflowed to it.
    416          */
    417 
    418         std     %l0, [%sp + CPU_STACK_FRAME_L0_OFFSET]
    419         std     %l2, [%sp + CPU_STACK_FRAME_L2_OFFSET]
    420         std     %l4, [%sp + CPU_STACK_FRAME_L4_OFFSET]
    421         std     %l6, [%sp + CPU_STACK_FRAME_L6_OFFSET]
    422 
    423         std     %i0, [%sp + CPU_STACK_FRAME_I0_OFFSET]
    424         std     %i2, [%sp + CPU_STACK_FRAME_I2_OFFSET]
    425         std     %i4, [%sp + CPU_STACK_FRAME_I4_OFFSET]
    426         std     %i6, [%sp + CPU_STACK_FRAME_I6_FP_OFFSET]
    427 
    428         restore
    429         nop
    430 
    431 dont_do_the_window:
    432         /*
    433          *  Global registers %g4 and %g5 are saved directly from %l4 and
    434          *  %l5 directly into the ISF below.
    435          */
    436 
    437 save_isf:
    438 
    439         /*
    440          *  Save the state of the interrupted task -- especially the global
    441          *  registers -- in the Interrupt Stack Frame.  Note that the ISF
    442          *  includes a regular minimum stack frame which will be used if
    443          *  needed by register window overflow and underflow handlers.
    444          *
    445          *  REGISTERS SAME AS AT _ISR_Handler
    446          */
    447 
    448         sub     %fp, CONTEXT_CONTROL_INTERRUPT_FRAME_SIZE, %sp
    449                                                ! make space for ISF
    450 
    451         std     %l0, [%sp + ISF_PSR_OFFSET]    ! save psr, PC
    452         st      %l2, [%sp + ISF_NPC_OFFSET]    ! save nPC
    453         st      %g1, [%sp + ISF_G1_OFFSET]     ! save g1
    454         std     %g2, [%sp + ISF_G2_OFFSET]     ! save g2, g3
    455         std     %l4, [%sp + ISF_G4_OFFSET]     ! save g4, g5 -- see above
    456         std     %g6, [%sp + ISF_G6_OFFSET]     ! save g6, g7
    457 
    458         std     %i0, [%sp + ISF_I0_OFFSET]     ! save i0, i1
    459         std     %i2, [%sp + ISF_I2_OFFSET]     ! save i2, i3
    460         std     %i4, [%sp + ISF_I4_OFFSET]     ! save i4, i5
    461         std     %i6, [%sp + ISF_I6_FP_OFFSET]  ! save i6/fp, i7
    462 
    463         rd      %y, %g1
    464         st      %g1, [%sp + ISF_Y_OFFSET]      ! save y
    465         st      %l6, [%sp + ISF_TPC_OFFSET]    ! save real trapped pc
    466 
    467         mov     %sp, %o1                       ! 2nd arg to ISR Handler
    468 
    469         /*
    470          *  Increment ISR nest level and Thread dispatch disable level.
    471          *
    472          *  Register usage for this section:
    473          *
    474          *    l4 = _Thread_Dispatch_disable_level pointer
    475          *    l5 = per cpu info pointer
    476          *    l6 = _Thread_Dispatch_disable_level value
    477          *    l7 = _ISR_Nest_level value
    478          *
    479          *  NOTE: It is assumed that l4 - l7 will be preserved until the ISR
    480          *        nest and thread dispatch disable levels are unnested.
    481          */
    482 
    483         sethi    %hi(SYM(_Thread_Dispatch_disable_level)), %l4
    484         ld       [%l4 + %lo(SYM(_Thread_Dispatch_disable_level))], %l6
    485 
    486         sethi    %hi(_Per_CPU_Information), %l5
    487         add      %l5, %lo(_Per_CPU_Information), %l5
    488 
    489         ld       [%l5 + PER_CPU_ISR_NEST_LEVEL], %l7
    490 
    491         add      %l6, 1, %l6
    492         st       %l6, [%l4 + %lo(SYM(_Thread_Dispatch_disable_level))]
    493 
    494         add      %l7, 1, %l7
    495         st       %l7, [%l5 + PER_CPU_ISR_NEST_LEVEL]
    496 
    497         /*
    498          *  If ISR nest level was zero (now 1), then switch stack.
    499          */
    500 
    501         mov      %sp, %fp
    502         subcc    %l7, 1, %l7             ! outermost interrupt handler?
    503         bnz      dont_switch_stacks      ! No, then do not switch stacks
    504 
    505         nop
    506         ld       [%l5 + PER_CPU_INTERRUPT_STACK_HIGH], %sp
    507 
    508 dont_switch_stacks:
    509         /*
    510          *  Make sure we have a place on the stack for the window overflow
    511          *  trap handler to write into.  At this point it is safe to
    512          *  enable traps again.
    513          */
    514 
    515         sub      %sp, CPU_MINIMUM_STACK_FRAME_SIZE, %sp
    516 
    517         /*
    518          *  Check if we have an external interrupt (trap 0x11 - 0x1f). If so,
    519          *  set the PIL in the %psr to mask off interrupts with lower priority.
    520          *  The original %psr in %l0 is not modified since it will be restored
    521          *  when the interrupt handler returns.
    522          */
    523 
    524         mov      %l0, %g5
    525         and      %l3, 0x0ff, %g4
    526 
    527 /* This is a fix for ERC32 with FPU rev.B or rev.C */
    528 
    529 #if defined(FPU_REVB)
    530 
    531 
    532         subcc    %g4, 0x08, %g0
    533         be       fpu_revb
    534         subcc    %g4, 0x11, %g0
    535         bl       dont_fix_pil
    536         subcc    %g4, 0x1f, %g0
    537         bg       dont_fix_pil
    538         sll      %g4, 8, %g4
    539         and      %g4, SPARC_PSR_PIL_MASK, %g4
    540         andn     %l0, SPARC_PSR_PIL_MASK, %g5
    541         or       %g4, %g5, %g5
    542         srl      %l0, 12, %g4
    543         andcc    %g4, 1, %g0
    544         be       dont_fix_pil
    545         nop
    546         ba,a     enable_irq
    547 
    548 
    549 fpu_revb:
    550         srl      %l0, 12, %g4   ! check if EF is set in %psr
    551         andcc    %g4, 1, %g0
    552         be       dont_fix_pil   ! if FPU disabled than continue as normal
    553         and      %l3, 0xff, %g4
    554         subcc    %g4, 0x08, %g0
    555         bne      enable_irq     ! if not a FPU exception then do two fmovs
    556         set      __sparc_fq, %g4
    557         st       %fsr, [%g4]    ! if FQ is not empty and FQ[1] = fmovs
    558         ld       [%g4], %g4     ! than this is bug 3.14
    559         srl      %g4, 13, %g4
    560         andcc    %g4, 1, %g0
    561         be       dont_fix_pil
    562         set      __sparc_fq, %g4
    563         std      %fq, [%g4]
    564         ld       [%g4+4], %g4
    565         set      0x81a00020, %g5
    566         subcc    %g4, %g5, %g0
    567         bne,a    dont_fix_pil2
    568         wr       %l0, SPARC_PSR_ET_MASK, %psr ! **** ENABLE TRAPS ****
    569         ba,a     simple_return
    570        
    571 enable_irq:
    572         or       %g5, SPARC_PSR_PIL_MASK, %g4
    573         wr       %g4, SPARC_PSR_ET_MASK, %psr ! **** ENABLE TRAPS ****
    574         nop; nop; nop
    575         fmovs    %f0, %f0
    576         ba       dont_fix_pil
    577         fmovs    %f0, %f0
    578 
    579         .data
    580         .global __sparc_fq
    581         .align 8
    582 __sparc_fq:
    583         .word 0,0
    584 
    585         .text
    586 /* end of ERC32 FPU rev.B/C fix */
    587 
    588 #else
    589 
    590         subcc    %g4, 0x11, %g0
    591         bl       dont_fix_pil
    592         subcc    %g4, 0x1f, %g0
    593         bg       dont_fix_pil
    594         sll      %g4, 8, %g4
    595         and      %g4, SPARC_PSR_PIL_MASK, %g4
    596         andn     %l0, SPARC_PSR_PIL_MASK, %g5
    597         ba       pil_fixed
    598         or       %g4, %g5, %g5
     347        mov     %psr, %g1               ! Initialize WIM
     348        add     %g1, 1, %g2
     349        and     %g2, 0x7, %g2
     350        set     1, %g3
     351        sll     %g3, %g2, %g3
     352        mov     %g3, %wim
     353        ba      done_flushing
     354        mov     %i0, %o1                      ! in the delay slot
    599355#endif
    600356
    601 dont_fix_pil:
    602         or       %g5, SPARC_PSR_PIL_MASK, %g5
    603 pil_fixed:
    604         wr       %g5, SPARC_PSR_ET_MASK, %psr ! **** ENABLE TRAPS ****
    605 dont_fix_pil2:
    606 
    607         /*
    608          *  Vector to user's handler.
    609          *
    610          *  NOTE: TBR may no longer have vector number in it since
    611          *        we just enabled traps.  It is definitely in l3.
    612          */
    613 
    614         sethi    %hi(SYM(_ISR_Vector_table)), %g4
    615         ld       [%g4+%lo(SYM(_ISR_Vector_table))], %g4
    616         and      %l3, 0xFF, %g5         ! remove synchronous trap indicator
    617         sll      %g5, 2, %g5            ! g5 = offset into table
    618         ld       [%g4 + %g5], %g4       ! g4 = _ISR_Vector_table[ vector ]
    619 
    620 
    621                                         ! o1 = 2nd arg = address of the ISF
    622                                         !   WAS LOADED WHEN ISF WAS SAVED!!!
    623         mov      %l3, %o0               ! o0 = 1st arg = vector number
    624         call     %g4, 0
    625         nop                             ! delay slot
    626 
    627         /*
    628          *  Redisable traps so we can finish up the interrupt processing.
    629          *  This is a VERY conservative place to do this.
    630          *
    631          *  NOTE: %l0 has the PSR which was in place when we took the trap.
    632          */
    633 
    634         mov      %l0, %psr             ! **** DISABLE TRAPS ****
    635         nop; nop; nop
    636 
    637         /*
    638          *  Decrement ISR nest level and Thread dispatch disable level.
    639          *
    640          *  Register usage for this section:
    641          *
    642          *    l4 = _Thread_Dispatch_disable_level pointer
    643          *    l5 = _ISR_Nest_level pointer
    644          *    l6 = _Thread_Dispatch_disable_level value
    645          *    l7 = _ISR_Nest_level value
    646          */
    647 
    648         sub      %l6, 1, %l6
    649         st       %l6, [%l4 + %lo(SYM(_Thread_Dispatch_disable_level))]
    650 
    651         st       %l7, [%l5 + PER_CPU_ISR_NEST_LEVEL]
    652 
    653         /*
    654          *  If dispatching is disabled (includes nested interrupt case),
    655          *  then do a "simple" exit.
    656          */
    657 
    658         orcc     %l6, %g0, %g0   ! Is dispatching disabled?
    659         bnz      simple_return   ! Yes, then do a "simple" exit
    660         ! NOTE: Use the delay slot
    661         sethi    %hi(SYM(_CPU_ISR_Dispatch_disable)), %l6
    662 
    663         ! Are we dispatching from a previous ISR in the interrupted thread?
    664         ld       [%l6 + %lo(SYM(_CPU_ISR_Dispatch_disable))], %l7
    665         orcc     %l7, %g0, %g0   ! Is this thread already doing an ISR?
    666         bnz      simple_return   ! Yes, then do a "simple" exit
    667         nop
    668 
    669 
    670         /*
    671          *  If a context switch is necessary, then do fudge stack to
    672          *  return to the interrupt dispatcher.
    673          */
    674 
    675         ldub     [%l5 + PER_CPU_DISPATCH_NEEDED], %l5
    676 
    677         orcc     %l5, %g0, %g0   ! Is thread switch necessary?
    678         bz       simple_return   ! no, then do a simple return
    679         nop
    680 
    681         /*
    682          *  Invoke interrupt dispatcher.
    683          */
    684 
    685         PUBLIC(_ISR_Dispatch)
    686 SYM(_ISR_Dispatch):
    687         ! Set ISR dispatch nesting prevention flag
    688         mov      1,%l6
    689         sethi    %hi(SYM(_CPU_ISR_Dispatch_disable)), %l5
    690         st       %l6,[%l5 + %lo(SYM(_CPU_ISR_Dispatch_disable))]
    691 
    692         /*
    693          *  The following subtract should get us back on the interrupted
    694          *  tasks stack and add enough room to invoke the dispatcher.
    695          *  When we enable traps, we are mostly back in the context
    696          *  of the task and subsequent interrupts can operate normally.
    697          */
    698 
    699         sub      %fp, CPU_MINIMUM_STACK_FRAME_SIZE, %sp
    700 
    701         or      %l0, SPARC_PSR_ET_MASK, %l7    ! l7 = PSR with ET=1
    702         mov     %l7, %psr                      !  **** ENABLE TRAPS ****
    703         nop
    704         nop
    705         nop
    706 isr_dispatch:
    707         call    SYM(_Thread_Dispatch), 0
    708         nop
    709 
    710         /*
    711          *  We invoked _Thread_Dispatch in a state similar to the interrupted
    712          *  task.  In order to safely be able to tinker with the register
    713          *  windows and get the task back to its pre-interrupt state,
    714          *  we need to disable interrupts disabled so we can safely tinker
    715          *  with the register windowing.  In particular, the CWP in the PSR
    716          *  is fragile during this period. (See PR578.)
    717          */
    718         mov     2,%g1                           ! syscall (disable interrupts)
    719         ta      0                               ! syscall (disable interrupts)
    720 
    721         /*
    722          *  While we had ISR dispatching disabled in this thread,
    723          *  did we miss anything.  If so, then we need to do another
    724          *  _Thread_Dispatch before leaving this ISR Dispatch context.
    725          */
    726 
    727         sethi    %hi(_Per_CPU_Information), %l5
    728         add      %l5, %lo(_Per_CPU_Information), %l5
    729 
    730         ldub     [%l5 + PER_CPU_DISPATCH_NEEDED], %l7
    731 
    732         orcc     %l7, %g0, %g0    ! Is thread switch necesary?
    733         bz       allow_nest_again ! No, then clear out and return
    734         nop
    735 
    736         ! Yes, then invoke the dispatcher
    737 dispatchAgain:
    738         mov     3,%g1                           ! syscall (enable interrupts)
    739         ta      0                               ! syscall (enable interrupts)
    740         ba      isr_dispatch
    741         nop
    742 
    743 allow_nest_again:
    744 
    745         ! Zero out ISR stack nesting prevention flag
    746         sethi    %hi(SYM(_CPU_ISR_Dispatch_disable)), %l5
    747         st       %g0,[%l5 + %lo(SYM(_CPU_ISR_Dispatch_disable))]
    748 
    749         /*
    750          *  The CWP in place at this point may be different from
    751          *  that which was in effect at the beginning of the ISR if we
    752          *  have been context switched between the beginning of this invocation
    753          *  of _ISR_Handler and this point.  Thus the CWP and WIM should
    754          *  not be changed back to their values at ISR entry time.  Any
    755          *  changes to the PSR must preserve the CWP.
    756          */
    757 
    758 simple_return:
    759         ld      [%fp + ISF_Y_OFFSET], %l5      ! restore y
    760         wr      %l5, 0, %y
    761 
    762         ldd     [%fp + ISF_PSR_OFFSET], %l0    ! restore psr, PC
    763         ld      [%fp + ISF_NPC_OFFSET], %l2    ! restore nPC
    764         rd      %psr, %l3
    765         and     %l3, SPARC_PSR_CWP_MASK, %l3   ! want "current" CWP
    766         andn    %l0, SPARC_PSR_CWP_MASK, %l0   ! want rest from task
    767         or      %l3, %l0, %l0                  ! install it later...
    768         andn    %l0, SPARC_PSR_ET_MASK, %l0
    769 
    770         /*
    771          *  Restore tasks global and out registers
    772          */
    773 
    774         mov    %fp, %g1
    775 
    776                                               ! g1 is restored later
    777         ldd     [%fp + ISF_G2_OFFSET], %g2    ! restore g2, g3
    778         ldd     [%fp + ISF_G4_OFFSET], %g4    ! restore g4, g5
    779         ldd     [%fp + ISF_G6_OFFSET], %g6    ! restore g6, g7
    780 
    781         ldd     [%fp + ISF_I0_OFFSET], %i0    ! restore i0, i1
    782         ldd     [%fp + ISF_I2_OFFSET], %i2    ! restore i2, i3
    783         ldd     [%fp + ISF_I4_OFFSET], %i4    ! restore i4, i5
    784         ldd     [%fp + ISF_I6_FP_OFFSET], %i6 ! restore i6/fp, i7
    785 
    786         /*
    787          *  Registers:
    788          *
    789          *   ALL global registers EXCEPT G1 and the input registers have
    790          *   already been restored and thuse off limits.
    791          *
    792          *   The following is the contents of the local registers:
    793          *
    794          *     l0 = original psr
    795          *     l1 = return address (i.e. PC)
    796          *     l2 = nPC
    797          *     l3 = CWP
    798          */
    799 
    800         /*
    801          *  if (CWP + 1) is an invalid window then we need to reload it.
    802          *
    803          *  WARNING: Traps should now be disabled
    804          */
    805 
    806         mov     %l0, %psr                  !  **** DISABLE TRAPS ****
    807         nop
    808         nop
    809         nop
    810         rd      %wim, %l4
    811         add     %l0, 1, %l6                ! l6 = cwp + 1
    812         and     %l6, SPARC_PSR_CWP_MASK, %l6 ! do the modulo on it
    813         srl     %l4, %l6, %l5              ! l5 = win >> cwp + 1 ; shift count
    814                                            !  and CWP are conveniently LS 5 bits
    815         cmp     %l5, 1                     ! Is tasks window invalid?
    816         bne     good_task_window
    817 
    818         /*
    819          *  The following code is the same as a 1 position left rotate of WIM.
    820          */
    821 
    822         sll     %l4, 1, %l5                ! l5 = WIM << 1
    823         srl     %l4, SPARC_NUMBER_OF_REGISTER_WINDOWS-1 , %l4
    824                                            ! l4 = WIM >> (Number Windows - 1)
    825         or      %l4, %l5, %l4              ! l4 = (WIM << 1) |
    826                                            !      (WIM >> (Number Windows - 1))
    827 
    828         /*
    829          *  Now restore the window just as if we underflowed to it.
    830          */
    831 
    832         wr      %l4, 0, %wim               ! WIM = new WIM
    833         nop                                ! must delay after writing WIM
    834         nop
    835         nop
    836         restore                            ! now into the tasks window
    837 
    838         ldd     [%g1 + CPU_STACK_FRAME_L0_OFFSET], %l0
    839         ldd     [%g1 + CPU_STACK_FRAME_L2_OFFSET], %l2
    840         ldd     [%g1 + CPU_STACK_FRAME_L4_OFFSET], %l4
    841         ldd     [%g1 + CPU_STACK_FRAME_L6_OFFSET], %l6
    842         ldd     [%g1 + CPU_STACK_FRAME_I0_OFFSET], %i0
    843         ldd     [%g1 + CPU_STACK_FRAME_I2_OFFSET], %i2
    844         ldd     [%g1 + CPU_STACK_FRAME_I4_OFFSET], %i4
    845         ldd     [%g1 + CPU_STACK_FRAME_I6_FP_OFFSET], %i6
    846                                            ! reload of sp clobbers ISF
    847         save                               ! Back to ISR dispatch window
    848 
    849 good_task_window:
    850 
    851         mov     %l0, %psr                  !  **** DISABLE TRAPS ****
    852         nop; nop; nop
    853                                            !  and restore condition codes.
    854         ld      [%g1 + ISF_G1_OFFSET], %g1 ! restore g1
    855         jmp     %l1                        ! transfer control and
    856         rett    %l2                        ! go back to tasks window
    857 
    858357/* end of file */
  • cpukit/score/cpu/sparc/rtems/score/cpu.h

    RCS file: /usr1/CVS/rtems/cpukit/score/cpu/sparc/rtems/score/cpu.h,v
    retrieving revision 1.38
    diff -u -r1.38 cpu.h
     
    66 *  This include file contains information pertaining to the port of
    77 *  the executive to the SPARC processor.
    88 *
    9  *  COPYRIGHT (c) 1989-2006.
     9 *  COPYRIGHT (c) 1989-2011.
    1010 *  On-Line Applications Research Corporation (OAR).
    1111 *
    1212 *  The license and distribution terms for this file may be
     
    927927  Context_Control *new_context
    928928) RTEMS_COMPILER_NO_RETURN_ATTRIBUTE;
    929929
     930#if defined(RTEMS_SMP)
     931/*
     932 *  _CPU_Context_switch_to_first_task_smp
     933 *
     934 *  This routine is only used to switch to the first task on a
     935 *  secondary core in an SMP configuration.  We do not need to
     936 *  flush all the windows and, in fact, this can be dangerous
     937 *  as they may or may not be initialized properly.
     938 */
     939void _CPU_Context_switch_to_first_task_smp(
     940  Context_Control *new_context
     941);
     942#endif
     943
    930944/*
    931945 *  _CPU_Context_save_fp
    932946 *
  • cpukit/score/include/rtems/score/context.h

    RCS file: /usr1/CVS/rtems/cpukit/score/include/rtems/score/context.h,v
    retrieving revision 1.22
    diff -u -r1.22 context.h
     
    55 */
    66
    77/*
    8  *  COPYRIGHT (c) 1989-2006.
     8 *  COPYRIGHT (c) 1989-2011.
    99 *  On-Line Applications Research Corporation (OAR).
    1010 *
    1111 *  The license and distribution terms for this file may be
     
    4545
    4646/**
    4747 *  @brief Initialize Context Area
     48 *
    4849 *  This routine initializes @a _the_context such that the stack
    4950 *  pointer, interrupt level, and entry point are correct for the
    5051 *  thread's initial state.
     
    100101#define _Context_Restart_self( _the_context ) \
    101102   _CPU_Context_Restart_self( _the_context )
    102103
     104#if defined(RTEMS_SMP)
     105/*
     106 *  @brief Switch to First Task on Secondary Core
     107 *
     108 *  This routine is only used to switch to the first task on a
     109 *  secondary core in an SMP configuration.  Since the switch
     110 *  to the first task is done from an interrupt handler, this
     111 *  may be different from simply restarting the currently running
     112 *  task.
     113 *
     114 *  @param[in] _the_context is the context of the first thread to
     115 *             run on this core
     116 */
     117#define _Context_Switch_to_first_task_smp( _the_context ) \
     118   _CPU_Context_switch_to_first_task_smp( _the_context )
     119#endif
     120
    103121/**
    104122 *  @brief Return Starting Address of Floating Point Context
    105123 *
  • cpukit/score/include/rtems/score/percpu.h

    RCS file: /usr1/CVS/rtems/cpukit/score/include/rtems/score/percpu.h,v
    retrieving revision 1.4
    diff -u -r1.4 percpu.h
     
    11/**
    2  *  @file  rtems/score/percpu.h
     2 *  @file  rtems/percpu.h
    33 *
    44 *  This include file defines the per CPU information required
    55 *  by RTEMS.
    66 */
    77
    88/*
    9  *  COPYRIGHT (c) 1989-2010.
     9 *  COPYRIGHT (c) 1989-2011.
    1010 *  On-Line Applications Research Corporation (OAR).
    1111 *
    1212 *  The license and distribution terms for this file may be
    1313 *  found in the file LICENSE in this distribution or at
    1414 *  http://www.rtems.com/license/LICENSE.
    1515 *
    16  *  $Id: percpu.h,v 1.4 2010/07/30 18:53:06 joel Exp $
     16 *  $Id$
    1717 */
    1818
    1919#ifndef _RTEMS_PERCPU_H
     
    2323
    2424#ifdef ASM
    2525  #include <rtems/asm.h>
     26#else
     27  #if defined(RTEMS_SMP)
     28    #include <rtems/score/lock.h>
     29  #endif
    2630#endif
    2731
    2832/**
     
    4145#endif
    4246
    4347#ifndef ASM
     48#ifndef __THREAD_CONTROL_DEFINED__
     49#define __THREAD_CONTROL_DEFINED__
     50typedef struct Thread_Control_struct Thread_Control;
     51#endif
     52
     53#if (CPU_ALLOCATE_INTERRUPT_STACK == FALSE) && defined(RTEMS_SMP)
     54  #error "RTEMS must allocate per CPU interrupt stack for SMP"
     55#endif
     56 
     57/**
     58 *  This defines the constant used to indicate that the cpu code is in
     59 *  its initial powered up start.
     60 */
     61#define RTEMS_BSP_SMP_CPU_INITIAL_STATE 1
    4462
    4563/**
    46  * This forward defines the Thread Control Block structure.
     64 *  This defines the constant used to indicate that the cpu code has
     65 *  completed basic initialization and awaits further commands.
    4766 */
    48 typedef struct Thread_Control_struct Thread_Control;
     67#define RTEMS_BSP_SMP_CPU_INITIALIZED  2
    4968
    5069/**
    51  *  @brief Per CPU Core Structure
     70 *  This defines the constant used to indicate that the cpu code has
     71 *  shut itself down.
     72 */
     73#define RTEMS_BSP_SMP_CPU_SHUTDOWN  3
     74
     75/**
     76 *  @brief Per CPU Core BSP Structure
    5277 *
    5378 *  This structure is used to hold per core state information.
     79 *
     80 *  @note There will also be a SuperCore per cpu structure.  Some of these
     81 *        may move there.  In particular, the starting interrupt stack pointer
     82 *        makes sense to move there since the OS per CPU structure will
     83 *        need to be used for EVERY ISR received.  Then this structure will
     84 *        only needed from C.  But until that structure exists and
     85 *        RTEMS does SMP scheduling, we will just leave everything here.
    5486 */
    5587typedef struct {
     88  #if defined(RTEMS_SMP)
     89    /** This element is used to lock this structure */
     90    rtems_lock_t  Lock;
     91
     92    /** This indicates that the CPU is online. */
     93    volatile uint32_t  state;
     94
     95    /**
     96     *  This is the request for the interrupt.
     97     * 
     98     *  @note This may become a chain protected by atomic instructions.
     99     */
     100    volatile uint32_t  message;
     101  #endif
     102
    56103#if (CPU_ALLOCATE_INTERRUPT_STACK == TRUE) || \
    57104    (CPU_HAS_SOFTWARE_INTERRUPT_STACK == TRUE)
    58105  /**
    59106   * This contains a pointer to the lower range of the interrupt stack for
    60107   * this CPU.  This is the address allocated and freed.
    61108   */
    62   void  *interrupt_stack_low;
     109  void  *interrupt_stack_low; 
    63110
    64111  /**
    65112   * This contains a pointer to the interrupt stack pointer for this CPU.
    66113   * It will be loaded at the beginning on an ISR.
    67114   */
    68   void  *interrupt_stack_high;
     115  void  *interrupt_stack_high; 
    69116#endif
    70117
    71118  /**
     
    91138#endif
    92139
    93140#ifdef ASM
     141#if defined(RTEMS_SMP)
     142  #define PER_CPU_LOCK     0
     143  #define PER_CPU_STATE    (1 * __RTEMS_SIZEOF_VOID_P__)
     144  #define PER_CPU_MESSAGE  (2 * __RTEMS_SIZEOF_VOID_P__)
     145  #define PER_CPU_END_SMP  (3 * __RTEMS_SIZEOF_VOID_P__)
     146#else
     147  #define PER_CPU_END_SMP  0
     148#endif
    94149
    95150#if (CPU_ALLOCATE_INTERRUPT_STACK == TRUE) || \
    96151    (CPU_HAS_SOFTWARE_INTERRUPT_STACK == TRUE)
     
    98153   *  If this CPU target lets RTEMS allocates the interrupt stack, then
    99154   *  we need to have places in the per cpu table to hold them.
    100155   */
    101   #define PER_CPU_INTERRUPT_STACK_LOW   0
    102   #define PER_CPU_INTERRUPT_STACK_HIGH  (1 * __RTEMS_SIZEOF_VOID_P__)
    103   #define PER_CPU_END_STACK             (2 * __RTEMS_SIZEOF_VOID_P__)
     156  #define PER_CPU_INTERRUPT_STACK_LOW   PER_CPU_END_SMP
     157  #define PER_CPU_INTERRUPT_STACK_HIGH  \
     158          PER_CPU_INTERRUPT_STACK_LOW + (1 * __RTEMS_SIZEOF_VOID_P__)
     159  #define PER_CPU_END_STACK             \
     160          PER_CPU_INTERRUPT_STACK_HIGH + (1 * __RTEMS_SIZEOF_VOID_P__)
    104161#else
    105   /*
    106    *  Otherwise, there are no interrupt stack addresses in the per CPU table.
    107    */
    108   #define PER_CPU_END_STACK             0
     162  #define PER_CPU_END_STACK             PER_CPU_END_SMP
    109163#endif
    110164
    111165/*
     
    147201 *
    148202 *  This is an array of per CPU core information.
    149203 */
    150 extern Per_CPU_Control _Per_CPU_Information;
     204#if defined(RTEMS_SMP)
     205  extern Per_CPU_Control *_Per_CPU_Information;
     206#else
     207  extern Per_CPU_Control _Per_CPU_Information;
     208#endif
     209
     210#if defined(RTEMS_SMP)
     211/**
     212 *  @brief Set of Pointers to Per CPU Core Information
     213 *
     214 *  This is an array of pointers to each CPU's per CPU data structure.
     215 *  It should be simpler to retrieve this pointer in assembly language
     216 *  that to calculate the array offset.
     217 */
     218extern Per_CPU_Control **Per_CPU_Information_p;
     219
     220/**
     221 *  @brief Allocate and Initialize Per CPU Structures
     222 *
     223 *  This method allocates and initialize the per CPU structure.
     224 */
     225void _Per_CPU_Initialize(void);
     226
     227/* BSP provided routine */
     228int rtems_bsp_smp_get_current(void)  __attribute__ ((pure));
     229
     230#endif
    151231
    152232/*
    153233 * On an SMP system, these macros dereference the CPU core number.
    154234 * But on a non-SMP system, these macros are simple references.
    155235 * Thus when built for non-SMP, there should be no performance penalty.
    156236 */
    157 #define _Thread_Heir              _Per_CPU_Information.heir
    158 #define _Thread_Executing         _Per_CPU_Information.executing
    159 #define _Thread_Idle              _Per_CPU_Information.idle
    160 #define _ISR_Nest_level           _Per_CPU_Information.isr_nest_level
    161 #define _CPU_Interrupt_stack_low  _Per_CPU_Information.interrupt_stack_low
    162 #define _CPU_Interrupt_stack_high _Per_CPU_Information.interrupt_stack_high
    163 #define _Thread_Dispatch_necessary _Per_CPU_Information.dispatch_necessary
     237#if defined(RTEMS_SMP)
     238  #define _Thread_Heir \
     239    _Per_CPU_Information[rtems_bsp_smp_get_current()].heir
     240  #define _Thread_Executing \
     241    _Per_CPU_Information[rtems_bsp_smp_get_current()].executing
     242  #define _Thread_Idle \
     243    _Per_CPU_Information[rtems_bsp_smp_get_current()].idle
     244  #define _ISR_Nest_level \
     245    _Per_CPU_Information[rtems_bsp_smp_get_current()].isr_nest_level
     246  #define _CPU_Interrupt_stack_low \
     247    _Per_CPU_Information[rtems_bsp_smp_get_current()].interrupt_stack_low
     248  #define _CPU_Interrupt_stack_high \
     249    _Per_CPU_Information[rtems_bsp_smp_get_current()].interrupt_stack_high
     250  #define _Thread_Dispatch_necessary \
     251    _Per_CPU_Information[rtems_bsp_smp_get_current()].dispatch_necessary
     252#else
     253  #define _Thread_Heir               _Per_CPU_Information.heir
     254  #define _Thread_Executing          _Per_CPU_Information.executing
     255  #define _Thread_Idle               _Per_CPU_Information.idle
     256  #define _ISR_Nest_level            _Per_CPU_Information.isr_nest_level
     257  #define _CPU_Interrupt_stack_low   _Per_CPU_Information.interrupt_stack_low
     258  #define _CPU_Interrupt_stack_high  _Per_CPU_Information.interrupt_stack_high
     259  #define _Thread_Dispatch_necessary _Per_CPU_Information.dispatch_necessary
     260#endif
    164261
    165262#endif  /* ASM */
    166263
  • cpukit/score/src/percpu.c

    RCS file: /usr1/CVS/rtems/cpukit/score/src/percpu.c,v
    retrieving revision 1.1
    diff -u -r1.1 percpu.c
     
    11/*
    2  *  COPYRIGHT (c) 1989-2010.
     2 *  COPYRIGHT (c) 1989-2011.
    33 *  On-Line Applications Research Corporation (OAR).
    44 *
    55 *  The license and distribution terms for this file may be
     
    2121#include <rtems/config.h>
    2222#include <string.h>
    2323
    24 /*
    25  * On single core systems, we can efficiently directly access a single
    26  * statically allocated per cpu structure.  And the fields are initialized
    27  * as individual elements just like it has always been done.
    28  */
    29 Per_CPU_Control _Per_CPU_Information;
     24#if defined(RTEMS_SMP)
     25  Per_CPU_Control *_Per_CPU_Information;
     26  Per_CPU_Control **_Per_CPU_Information_p;
     27  extern uint32_t rtems_smp_maximum_cpus;
     28
     29  void per_cpu_initialize(void)
     30  {
     31    int         cpu;
     32    size_t      size;
     33    uintptr_t   ptr;
     34
     35    /*
     36     *  Allocate and initialize per CPU structures.
     37     */
     38    size = (rtems_smp_maximum_cpus) * sizeof(Per_CPU_Control);
     39    _Per_CPU_Information =
     40      (Per_CPU_Control *)_Workspace_Allocate_or_fatal_error( size );
     41    memset( _Per_CPU_Information, '\0', size );
     42
     43    /*
     44     *  Allocate per cpu pointer table
     45     */
     46    size = (rtems_smp_maximum_cpus) * sizeof(Per_CPU_Control *);
     47
     48    _Per_CPU_Information_p =
     49      (Per_CPU_Control **)_Workspace_Allocate_or_fatal_error( size );
     50
     51    size = Configuration.interrupt_stack_size;
     52    _Per_CPU_Information_p[0] = &_Per_CPU_Information[0];
     53    for (cpu=1 ; cpu < rtems_smp_maximum_cpus ; cpu++ ) {
     54      Per_CPU_Control *p = &_Per_CPU_Information[cpu];
     55
     56      _Per_CPU_Information_p[cpu] = p;
     57
     58      p->interrupt_stack_low = _Workspace_Allocate_or_fatal_error( size );
     59
     60      ptr = (uintptr_t) _Addresses_Add_offset( p->interrupt_stack_low, size );
     61      ptr &= ~CPU_STACK_ALIGNMENT;
     62      p->interrupt_stack_high = (void *)ptr;
     63      p->state = RTEMS_BSP_SMP_CPU_INITIAL_STATE;
     64    }
     65  }
     66#else
     67
     68  /*
     69   * On single core systems, we can efficiently directly access a single
     70   * statically allocated per cpu structure.  And the fields are initialized
     71   * as individual elements just like it has always been done.
     72   */
     73  Per_CPU_Control _Per_CPU_Information;
     74
     75#endif
  • cpukit/score/src/thread.c

    RCS file: /usr1/CVS/rtems/cpukit/score/src/thread.c,v
    retrieving revision 1.65
    diff -u -r1.65 thread.c
     
    22 *  Thread Handler
    33 *
    44 *
    5  *  COPYRIGHT (c) 1989-2008.
     5 *  COPYRIGHT (c) 1989-2011.
    66 *  On-Line Applications Research Corporation (OAR).
    77 *
    88 *  The license and distribution terms for this file may be
     
    3333#include <rtems/score/wkspace.h>
    3434#include <rtems/config.h>
    3535
    36 /*PAGE
    37  *
     36#if defined(RTEMS_SMP)
     37  #include <rtems/bspsmp.h>
     38#endif
     39
     40/*
    3841 *  _Thread_Handler_initialization
    3942 *
    4043 *  This routine initializes all thread manager related data structures.
     
    4851{
    4952  uint32_t     ticks_per_timeslice;
    5053  uint32_t     maximum_extensions;
     54  uint32_t     maximum_internal_threads;
    5155  #if defined(RTEMS_MULTIPROCESSING)
    5256    uint32_t   maximum_proxies;
    5357  #endif
     
    8084
    8185  _Thread_Ticks_per_timeslice  = ticks_per_timeslice;
    8286
    83 #if defined(RTEMS_MULTIPROCESSING)
    84   _Thread_MP_Handler_initialization( maximum_proxies );
    85 #endif
     87  #if defined(RTEMS_MULTIPROCESSING)
     88    _Thread_MP_Handler_initialization( maximum_proxies );
     89  #endif
    8690
    8791  /*
    88    *  Initialize this class of objects.
     92   *  Initialize the internal class of threads.  We need an IDLE thread
     93   *  per CPU in an SMP system.  In addition, if this is a loosely
     94   *  coupled multiprocessing system, account for the MPCI Server Thread.
    8995   */
     96  #if defined(RTEMS_SMP)
     97    maximum_internal_threads = rtems_smp_maximum_cpus;
     98  #else
     99    maximum_internal_threads = 1;
     100  #endif
     101
     102  #if defined(RTEMS_MULTIPROCESSING)
     103    if ( _System_state_Is_multiprocessing )
     104      maximum_internal_threads += 1;
     105  #endif
    90106
    91107  _Objects_Initialize_information(
    92108    &_Thread_Internal_information,
    93109    OBJECTS_INTERNAL_API,
    94110    OBJECTS_INTERNAL_THREADS,
    95 #if defined(RTEMS_MULTIPROCESSING)
    96     ( _System_state_Is_multiprocessing ) ?  2 : 1,
    97 #else
    98     1,
    99 #endif
     111    maximum_internal_threads,
    100112    sizeof( Thread_Control ),
    101113                                /* size of this object's control block */
    102114    false,                      /* true if names for this object are strings */
    103115    8                           /* maximum length of each object's name */
    104 #if defined(RTEMS_MULTIPROCESSING)
    105     ,
    106     false,                      /* true if this is a global object class */
    107     NULL                        /* Proxy extraction support callout */
    108 #endif
     116    #if defined(RTEMS_MULTIPROCESSING)
     117      ,
     118      false,                      /* true if this is a global object class */
     119      NULL                        /* Proxy extraction support callout */
     120    #endif
    109121  );
    110122
    111123}
  • cpukit/score/src/threadcreateidle.c

    RCS file: /usr1/CVS/rtems/cpukit/score/src/threadcreateidle.c,v
    retrieving revision 1.15
    diff -u -r1.15 threadcreateidle.c
     
    22 *  Thread Handler
    33 *
    44 *
    5  *  COPYRIGHT (c) 1989-2008.
     5 *  COPYRIGHT (c) 1989-2011.
    66 *  On-Line Applications Research Corporation (OAR).
    77 *
    88 *  The license and distribution terms for this file may be
     
    3131#include <rtems/score/wkspace.h>
    3232#include <rtems/config.h>
    3333
    34 /*PAGE
    35  *
    36  *  _Thread_Create_idle
    37  */
     34#if defined(RTEMS_SMP)
     35  #include <rtems/bspsmp.h>
     36#endif
    3837
    39 void _Thread_Create_idle( void )
     38static inline void _Thread_Create_idle_helper(
     39  uint32_t name_u32
     40  #if defined(RTEMS_SMP)
     41    ,
     42    int    cpu
     43  #endif
     44)
    4045{
    41   Objects_Name name;
     46  Objects_Name    name;
     47  Thread_Control *idle;
    4248
    43   name.name_u32 = _Objects_Build_name( 'I', 'D', 'L', 'E' );
     49  name.name_u32 = name_u32;
    4450
    4551  /*
    4652   *  The entire workspace is zeroed during its initialization.  Thus, all
    4753   *  fields not explicitly assigned were explicitly zeroed by
    4854   *  _Workspace_Initialization.
    4955   */
    50   _Thread_Idle = _Thread_Internal_allocate();
     56  idle = _Thread_Internal_allocate();
    5157
    5258  /*
    5359   *  This is only called during initialization and we better be sure
     
    5864
    5965  _Thread_Initialize(
    6066    &_Thread_Internal_information,
    61     _Thread_Idle,
     67    idle,
    6268    NULL,        /* allocate the stack */
    6369    _Stack_Ensure_minimum( Configuration.idle_task_stack_size ),
    6470    CPU_IDLE_TASK_IS_FP,
     
    7682   *  WARNING!!! This is necessary to "kick" start the system and
    7783   *             MUST be done before _Thread_Start is invoked.
    7884   */
    79   _Thread_Heir      =
    80   _Thread_Executing = _Thread_Idle;
     85  #if defined(RTEMS_SMP)
     86    _Per_CPU_Information[ cpu ].idle      =
     87    _Per_CPU_Information[ cpu ].heir      =
     88    _Per_CPU_Information[ cpu ].executing = idle;
     89  #else
     90    _Thread_Idle      =
     91    _Thread_Heir      =
     92    _Thread_Executing = idle;
     93  #endif
    8194
    8295  _Thread_Start(
    83     _Thread_Idle,
     96    idle,
    8497    THREAD_START_NUMERIC,
    8598    Configuration.idle_task,
    8699    NULL,
    87100    0
    88101  );
     102}
     103
     104void _Thread_Create_idle( void )
     105{
     106  #if defined(RTEMS_SMP)
     107    int cpu;
    89108
     109    for ( cpu=0 ; cpu < rtems_smp_number_of_cpus ; cpu++ ) {
     110      _Thread_Create_idle_helper(
     111        _Objects_Build_name( 'I', 'D', 'L', 'E' ),
     112        cpu
     113      );
     114    }
     115  #else
     116    _Thread_Create_idle_helper(_Objects_Build_name( 'I', 'D', 'L', 'E' ));
     117  #endif
    90118}