source: rtems/cpukit/score/cpu/moxie/include/rtems/score/cpu.h @ 264e128

5
Last change on this file since 264e128 was 264e128, checked in by Sebastian Huber <sebastian.huber@…>, on 11/09/18 at 07:04:23

moxie: Remove use of proc_ptr

Update #3585.

  • Property mode set to 100644
File size: 19.7 KB
Line 
1/**
2 * @file rtems/score/cpu.h
3 */
4
5/*
6 *  This include file contains information pertaining to the Moxie
7 *  processor.
8 *
9 *  Copyright (c) 2013  Anthony Green
10 *
11 *  Based on code with the following copyright..
12 *  COPYRIGHT (c) 1989-2006, 2010.
13 *  On-Line Applications Research Corporation (OAR).
14 *
15 *  The license and distribution terms for this file may be
16 *  found in the file LICENSE in this distribution or at
17 *  http://www.rtems.org/license/LICENSE.
18 */
19
20#ifndef _RTEMS_SCORE_CPU_H
21#define _RTEMS_SCORE_CPU_H
22
23#ifdef __cplusplus
24extern "C" {
25#endif
26
27#include <rtems/score/basedefs.h>
28#include <rtems/score/moxie.h>  /* pick up machine definitions */
29
30#include <rtems/bspIo.h>        /* printk */
31
32/* conditional compilation parameters */
33
34/*
35 *  Should this target use 16 or 32 bit object Ids?
36 *
37 */
38#define RTEMS_USE_32_BIT_OBJECT
39
40/*
41 *  Does the CPU follow the simple vectored interrupt model?
42 *
43 *  If TRUE, then RTEMS allocates the vector table it internally manages.
44 *  If FALSE, then the BSP is assumed to allocate and manage the vector
45 *  table
46 *
47 *  MOXIE Specific Information:
48 *
49 *  XXX document implementation including references if appropriate
50 */
51#define CPU_SIMPLE_VECTORED_INTERRUPTS TRUE
52
53/*
54 *  Does the CPU have hardware floating point?
55 *
56 *  If TRUE, then the RTEMS_FLOATING_POINT task attribute is supported.
57 *  If FALSE, then the RTEMS_FLOATING_POINT task attribute is ignored.
58 *
59 *  If there is a FP coprocessor such as the i387 or mc68881, then
60 *  the answer is TRUE.
61 *
62 *  The macro name "MOXIE_HAS_FPU" should be made CPU specific.
63 *  It indicates whether or not this CPU model has FP support.  For
64 *  example, it would be possible to have an i386_nofp CPU model
65 *  which set this to false to indicate that you have an i386 without
66 *  an i387 and wish to leave floating point support out of RTEMS.
67 *
68 *  MOXIE Specific Information:
69 *
70 *  XXX
71 */
72#define CPU_HARDWARE_FP     FALSE
73
74/*
75 *  Are all tasks RTEMS_FLOATING_POINT tasks implicitly?
76 *
77 *  If TRUE, then the RTEMS_FLOATING_POINT task attribute is assumed.
78 *  If FALSE, then the RTEMS_FLOATING_POINT task attribute is followed.
79 *
80 *  If CPU_HARDWARE_FP is FALSE, then this should be FALSE as well.
81 *
82 *  MOXIE Specific Information:
83 *
84 *  XXX
85 */
86#define CPU_ALL_TASKS_ARE_FP     FALSE
87
88/*
89 *  Should the IDLE task have a floating point context?
90 *
91 *  If TRUE, then the IDLE task is created as a RTEMS_FLOATING_POINT task
92 *  and it has a floating point context which is switched in and out.
93 *  If FALSE, then the IDLE task does not have a floating point context.
94 *
95 *  Setting this to TRUE negatively impacts the time required to preempt
96 *  the IDLE task from an interrupt because the floating point context
97 *  must be saved as part of the preemption.
98 *
99 *  MOXIE Specific Information:
100 *
101 *  XXX
102 */
103#define CPU_IDLE_TASK_IS_FP      FALSE
104
105/*
106 *  Should the saving of the floating point registers be deferred
107 *  until a context switch is made to another different floating point
108 *  task?
109 *
110 *  If TRUE, then the floating point context will not be stored until
111 *  necessary.  It will remain in the floating point registers and not
112 *  disturned until another floating point task is switched to.
113 *
114 *  If FALSE, then the floating point context is saved when a floating
115 *  point task is switched out and restored when the next floating point
116 *  task is restored.  The state of the floating point registers between
117 *  those two operations is not specified.
118 *
119 *  If the floating point context does NOT have to be saved as part of
120 *  interrupt dispatching, then it should be safe to set this to TRUE.
121 *
122 *  Setting this flag to TRUE results in using a different algorithm
123 *  for deciding when to save and restore the floating point context.
124 *  The deferred FP switch algorithm minimizes the number of times
125 *  the FP context is saved and restored.  The FP context is not saved
126 *  until a context switch is made to another, different FP task.
127 *  Thus in a system with only one FP task, the FP context will never
128 *  be saved or restored.
129 *
130 *  MOXIE Specific Information:
131 *
132 *  XXX
133 */
134#define CPU_USE_DEFERRED_FP_SWITCH       TRUE
135
136#define CPU_ENABLE_ROBUST_THREAD_DISPATCH FALSE
137
138/*
139 *  Does the stack grow up (toward higher addresses) or down
140 *  (toward lower addresses)?
141 *
142 *  If TRUE, then the grows upward.
143 *  If FALSE, then the grows toward smaller addresses.
144 *
145 *  MOXIE Specific Information:
146 *
147 *  XXX
148 */
149#define CPU_STACK_GROWS_UP               FALSE
150
151/* FIXME: Is this the right value? */
152#define CPU_CACHE_LINE_BYTES 32
153
154#define CPU_STRUCTURE_ALIGNMENT
155
156/*
157 *  The following defines the number of bits actually used in the
158 *  interrupt field of the task mode.  How those bits map to the
159 *  CPU interrupt levels is defined by the routine _CPU_ISR_Set_level().
160 *
161 *  MOXIE Specific Information:
162 *
163 *  XXX
164 */
165#define CPU_MODES_INTERRUPT_MASK   0x00000001
166
167#define CPU_MAXIMUM_PROCESSORS 32
168
169/*
170 *  Processor defined structures required for cpukit/score.
171 *
172 *  MOXIE Specific Information:
173 *
174 *  XXX
175 */
176
177/* may need to put some structures here.  */
178
179/*
180 * Contexts
181 *
182 *  Generally there are 2 types of context to save.
183 *     1. Interrupt registers to save
184 *     2. Task level registers to save
185 *
186 *  This means we have the following 3 context items:
187 *     1. task level context stuff::  Context_Control
188 *     2. floating point task stuff:: Context_Control_fp
189 *     3. special interrupt level context :: Context_Control_interrupt
190 *
191 *  On some processors, it is cost-effective to save only the callee
192 *  preserved registers during a task context switch.  This means
193 *  that the ISR code needs to save those registers which do not
194 *  persist across function calls.  It is not mandatory to make this
195 *  distinctions between the caller/callee saves registers for the
196 *  purpose of minimizing context saved during task switch and on interrupts.
197 *  If the cost of saving extra registers is minimal, simplicity is the
198 *  choice.  Save the same context on interrupt entry as for tasks in
199 *  this case.
200 *
201 *  Additionally, if gdb is to be made aware of RTEMS tasks for this CPU, then
202 *  care should be used in designing the context area.
203 *
204 *  On some CPUs with hardware floating point support, the Context_Control_fp
205 *  structure will not be used or it simply consist of an array of a
206 *  fixed number of bytes.   This is done when the floating point context
207 *  is dumped by a "FP save context" type instruction and the format
208 *  is not really defined by the CPU.  In this case, there is no need
209 *  to figure out the exact format -- only the size.  Of course, although
210 *  this is enough information for RTEMS, it is probably not enough for
211 *  a debugger such as gdb.  But that is another problem.
212 *
213 *  MOXIE Specific Information:
214 *
215 *  XXX
216 */
217
218#define nogap __attribute__ ((packed))
219
220typedef struct {
221    void        *fp nogap;
222    void        *sp nogap;
223    uint32_t    r0 nogap;
224    uint32_t    r1 nogap;
225    uint32_t    r2 nogap;
226    uint32_t    r3 nogap;
227    uint32_t    r4 nogap;
228    uint32_t    r5 nogap;
229    uint32_t    r6 nogap;
230    uint32_t    r7 nogap;
231    uint32_t    r8 nogap;
232    uint32_t    r9 nogap;
233    uint32_t    r10 nogap;
234    uint32_t    r11 nogap;
235    uint32_t    r12 nogap;
236    uint32_t    r13 nogap;
237} Context_Control;
238
239#define _CPU_Context_Get_SP( _context ) \
240  (_context)->sp
241
242typedef struct {
243    double      some_float_register[2];
244} Context_Control_fp;
245
246typedef struct {
247    uint32_t   special_interrupt_register;
248} CPU_Interrupt_frame;
249
250/*
251 *  Nothing prevents the porter from declaring more CPU specific variables.
252 *
253 *  MOXIE Specific Information:
254 *
255 *  XXX
256 */
257
258/*
259 *  The size of the floating point context area.  On some CPUs this
260 *  will not be a "sizeof" because the format of the floating point
261 *  area is not defined -- only the size is.  This is usually on
262 *  CPUs with a "floating point save context" instruction.
263 *
264 *  MOXIE Specific Information:
265 *
266 *  XXX
267 */
268#define CPU_CONTEXT_FP_SIZE sizeof( Context_Control_fp )
269
270/*
271 *  Amount of extra stack (above minimum stack size) required by
272 *  system initialization thread.  Remember that in a multiprocessor
273 *  system the system intialization thread becomes the MP server thread.
274 *
275 *  MOXIE Specific Information:
276 *
277 *  It is highly unlikely the MOXIE will get used in a multiprocessor system.
278 */
279#define CPU_MPCI_RECEIVE_SERVER_EXTRA_STACK 0
280
281/*
282 *  This defines the number of entries in the ISR_Vector_table managed
283 *  by RTEMS.
284 *
285 *  MOXIE Specific Information:
286 *
287 *  XXX
288 */
289#define CPU_INTERRUPT_NUMBER_OF_VECTORS      64
290#define CPU_INTERRUPT_MAXIMUM_VECTOR_NUMBER \
291    (CPU_INTERRUPT_NUMBER_OF_VECTORS - 1)
292
293/*
294 *  This is defined if the port has a special way to report the ISR nesting
295 *  level.  Most ports maintain the variable _ISR_Nest_level.
296 */
297#define CPU_PROVIDES_ISR_IS_IN_PROGRESS FALSE
298
299/*
300 *  Should be large enough to run all RTEMS tests.  This ensures
301 *  that a "reasonable" small application should not have any problems.
302 *
303 *  MOXIE Specific Information:
304 *
305 *  XXX
306 */
307#define CPU_STACK_MINIMUM_SIZE          (1536)
308
309/**
310 * Size of a pointer.
311 *
312 * This must be an integer literal that can be used by the assembler.  This
313 * value will be used to calculate offsets of structure members.  These
314 * offsets will be used in assembler code.
315 */
316#define CPU_SIZEOF_POINTER         4
317
318/*
319 *  CPU's worst alignment requirement for data types on a byte boundary.  This
320 *  alignment does not take into account the requirements for the stack.
321 *
322 *  MOXIE Specific Information:
323 *
324 *  XXX
325 */
326#define CPU_ALIGNMENT              8
327
328/*
329 *  This number corresponds to the byte alignment requirement for the
330 *  heap handler.  This alignment requirement may be stricter than that
331 *  for the data types alignment specified by CPU_ALIGNMENT.  It is
332 *  common for the heap to follow the same alignment requirement as
333 *  CPU_ALIGNMENT.  If the CPU_ALIGNMENT is strict enough for the heap,
334 *  then this should be set to CPU_ALIGNMENT.
335 *
336 *  NOTE:  This does not have to be a power of 2.  It does have to
337 *         be greater or equal to than CPU_ALIGNMENT.
338 *
339 *  MOXIE Specific Information:
340 *
341 *  XXX
342 */
343#define CPU_HEAP_ALIGNMENT         CPU_ALIGNMENT
344
345/*
346 *  This number corresponds to the byte alignment requirement for the
347 *  stack.  This alignment requirement may be stricter than that for the
348 *  data types alignment specified by CPU_ALIGNMENT.  If the CPU_ALIGNMENT
349 *  is strict enough for the stack, then this should be set to 0.
350 *
351 *  NOTE:  This must be a power of 2 either 0 or greater than CPU_ALIGNMENT.
352 *
353 *  MOXIE Specific Information:
354 *
355 *  XXX
356 */
357#define CPU_STACK_ALIGNMENT        0
358
359#define CPU_INTERRUPT_STACK_ALIGNMENT CPU_CACHE_LINE_BYTES
360
361/*
362 *  ISR handler macros
363 */
364
365/*
366 *  Support routine to initialize the RTEMS vector table after it is allocated.
367 */
368#define _CPU_Initialize_vectors()
369
370/*
371 *  Disable all interrupts for an RTEMS critical section.  The previous
372 *  level is returned in _level.
373 *
374 *  MOXIE Specific Information:
375 *
376 *  TODO: As of 7 October 2014, this method is not implemented.
377 */
378#define _CPU_ISR_Disable( _isr_cookie ) \
379  do { \
380    (_isr_cookie) = 0; \
381  } while (0)
382
383/*
384 *  Enable interrupts to the previous level (returned by _CPU_ISR_Disable).
385 *  This indicates the end of an RTEMS critical section.  The parameter
386 *  _level is not modified.
387 *
388 *  MOXIE Specific Information:
389 *
390 *  TODO: As of 7 October 2014, this method is not implemented.
391 */
392#define _CPU_ISR_Enable( _isr_cookie ) \
393  do { \
394    (_isr_cookie) = (_isr_cookie); \
395  } while (0)
396
397/*
398 *  This temporarily restores the interrupt to _level before immediately
399 *  disabling them again.  This is used to divide long RTEMS critical
400 *  sections into two or more parts.  The parameter _level is not
401 *  modified.
402 *
403 *  MOXIE Specific Information:
404 *
405 *  TODO: As of 7 October 2014, this method is not implemented.
406 */
407#define _CPU_ISR_Flash( _isr_cookie ) \
408  do { \
409    _CPU_ISR_Enable( _isr_cookie ); \
410    _CPU_ISR_Disable( _isr_cookie ); \
411  } while (0)
412
413RTEMS_INLINE_ROUTINE bool _CPU_ISR_Is_enabled( uint32_t level )
414{
415  return true;
416}
417
418/*
419 *  Map interrupt level in task mode onto the hardware that the CPU
420 *  actually provides.  Currently, interrupt levels which do not
421 *  map onto the CPU in a generic fashion are undefined.  Someday,
422 *  it would be nice if these were "mapped" by the application
423 *  via a callout.  For example, m68k has 8 levels 0 - 7, levels
424 *  8 - 255 would be available for bsp/application specific meaning.
425 *  This could be used to manage a programmable interrupt controller
426 *  via the rtems_task_mode directive.
427 *
428 *  MOXIE Specific Information:
429 *
430 *  TODO: As of 7 October 2014, this method is not implemented.
431 */
432#define _CPU_ISR_Set_level( _new_level )        \
433  {                                                     \
434    if (_new_level)   asm volatile ( "nop\n" );         \
435    else              asm volatile ( "nop\n" );         \
436  }
437
438uint32_t   _CPU_ISR_Get_level( void );
439
440/* end of ISR handler macros */
441
442/* Context handler macros */
443
444/*
445 *  Initialize the context to a state suitable for starting a
446 *  task after a context restore operation.  Generally, this
447 *  involves:
448 *
449 *     - setting a starting address
450 *     - preparing the stack
451 *     - preparing the stack and frame pointers
452 *     - setting the proper interrupt level in the context
453 *     - initializing the floating point context
454 *
455 *  This routine generally does not set any unnecessary register
456 *  in the context.  The state of the "general data" registers is
457 *  undefined at task start time.
458 *
459 *  NOTE: This is_fp parameter is TRUE if the thread is to be a floating
460 *        point thread.  This is typically only used on CPUs where the
461 *        FPU may be easily disabled by software such as on the SPARC
462 *        where the PSR contains an enable FPU bit.
463 *
464 *  MOXIE Specific Information:
465 *
466 *  TODO: As of 7 October 2014, this method does not ensure that the context
467 *  is set up with interrupts disabled/enabled as requested.
468 */
469#define CPU_CCR_INTERRUPTS_ON  0x80
470#define CPU_CCR_INTERRUPTS_OFF 0x00
471
472#define _CPU_Context_Initialize( _the_context, _stack_base, _size, \
473                                 _isr, _entry_point, _is_fp, _tls_area ) \
474  /* Locate Me */                                                  \
475  do {                                                             \
476    uintptr_t   _stack;                                            \
477                                                                   \
478    (void) _is_fp; /* avoid warning for being unused */            \
479    (void) _isr;   /* avoid warning for being unused */            \
480    _stack = ((uintptr_t)(_stack_base)) + (_size) - 8;             \
481    *((void (**)(void))(_stack)) = (_entry_point);                 \
482    _stack -= 4;                                                   \
483    (_the_context)->fp = (void *)_stack;                           \
484    (_the_context)->sp = (void *)_stack;                           \
485  } while (0)
486
487
488/*
489 *  This routine is responsible for somehow restarting the currently
490 *  executing task.  If you are lucky, then all that is necessary
491 *  is restoring the context.  Otherwise, there will need to be
492 *  a special assembly routine which does something special in this
493 *  case.  Context_Restore should work most of the time.  It will
494 *  not work if restarting self conflicts with the stack frame
495 *  assumptions of restoring a context.
496 *
497 *  MOXIE Specific Information:
498 *
499 *  XXX
500 */
501#define _CPU_Context_Restart_self( _the_context ) \
502   _CPU_Context_restore( (_the_context) );
503
504#define _CPU_Context_Initialize_fp( _destination ) \
505  memset( *( _destination ), 0, CPU_CONTEXT_FP_SIZE );
506
507/* end of Context handler macros */
508
509/* Fatal Error manager macros */
510
511/*
512 *  This routine copies _error into a known place -- typically a stack
513 *  location or a register, optionally disables interrupts, and
514 *  halts/stops the CPU.
515 *
516 *  MOXIE Specific Information:
517 *
518 *  XXX
519 */
520#define _CPU_Fatal_halt( _source, _error ) \
521        printk("Fatal Error %d.%lu Halted\n",_source,_error); \
522        for(;;)
523
524/* end of Fatal Error manager macros */
525
526#define CPU_USE_GENERIC_BITFIELD_CODE TRUE
527
528/* functions */
529
530/*
531 *  _CPU_Initialize
532 *
533 *  This routine performs CPU dependent initialization.
534 *
535 *  MOXIE Specific Information:
536 *
537 *  XXX
538 */
539void _CPU_Initialize(void);
540
541typedef void ( *CPU_ISR_handler )( uint32_t );
542
543void _CPU_ISR_install_vector(
544  uint32_t         vector,
545  CPU_ISR_handler  new_handler,
546  CPU_ISR_handler *old_handler
547);
548
549void *_CPU_Thread_Idle_body( uintptr_t );
550
551/*
552 *  _CPU_Context_switch
553 *
554 *  This routine switches from the run context to the heir context.
555 *
556 *  MOXIE Specific Information:
557 *
558 *  XXX
559 */
560void _CPU_Context_switch(
561  Context_Control  *run,
562  Context_Control  *heir
563);
564
565/*
566 *  _CPU_Context_restore
567 *
568 *  This routine is generallu used only to restart self in an
569 *  efficient manner.  It may simply be a label in _CPU_Context_switch.
570 *
571 *  NOTE: May be unnecessary to reload some registers.
572 *
573 *  MOXIE Specific Information:
574 *
575 *  XXX
576 */
577void _CPU_Context_restore(
578  Context_Control *new_context
579) RTEMS_NO_RETURN;
580
581/*
582 *  _CPU_Context_save_fp
583 *
584 *  This routine saves the floating point context passed to it.
585 *
586 *  MOXIE Specific Information:
587 *
588 *  XXX
589 */
590void _CPU_Context_save_fp(
591  Context_Control_fp **fp_context_ptr
592);
593
594/*
595 *  _CPU_Context_restore_fp
596 *
597 *  This routine restores the floating point context passed to it.
598 *
599 *  MOXIE Specific Information:
600 *
601 *  XXX
602 */
603void _CPU_Context_restore_fp(
604  Context_Control_fp **fp_context_ptr
605);
606
607/**
608 * @brief The set of registers that specifies the complete processor state.
609 *
610 * The CPU exception frame may be available in fatal error conditions like for
611 * example illegal opcodes, instruction fetch errors, or data access errors.
612 *
613 * @see rtems_fatal(), RTEMS_FATAL_SOURCE_EXCEPTION, and
614 * rtems_exception_frame_print().
615 */
616typedef struct {
617  uint32_t integer_registers [16];
618} CPU_Exception_frame;
619
620/**
621 * @brief Prints the exception frame via printk().
622 *
623 * @see rtems_fatal() and RTEMS_FATAL_SOURCE_EXCEPTION.
624 */
625void _CPU_Exception_frame_print( const CPU_Exception_frame *frame );
626
627/*  The following routine swaps the endian format of an unsigned int.
628 *  It must be static because it is referenced indirectly.
629 *
630 *  This version will work on any processor, but if there is a better
631 *  way for your CPU PLEASE use it.  The most common way to do this is to:
632 *
633 *     swap least significant two bytes with 16-bit rotate
634 *     swap upper and lower 16-bits
635 *     swap most significant two bytes with 16-bit rotate
636 *
637 *  Some CPUs have special instructions which swap a 32-bit quantity in
638 *  a single instruction (e.g. i486).  It is probably best to avoid
639 *  an "endian swapping control bit" in the CPU.  One good reason is
640 *  that interrupts would probably have to be disabled to ensure that
641 *  an interrupt does not try to access the same "chunk" with the wrong
642 *  endian.  Another good reason is that on some CPUs, the endian bit
643 *  endianness for ALL fetches -- both code and data -- so the code
644 *  will be fetched incorrectly.
645 *
646 *  MOXIE Specific Information:
647 *
648 *  This is the generic implementation.
649 */
650static inline uint32_t   CPU_swap_u32(
651  uint32_t   value
652)
653{
654  uint32_t   byte1, byte2, byte3, byte4, swapped;
655
656  byte4 = (value >> 24) & 0xff;
657  byte3 = (value >> 16) & 0xff;
658  byte2 = (value >> 8)  & 0xff;
659  byte1 =  value        & 0xff;
660
661  swapped = (byte1 << 24) | (byte2 << 16) | (byte3 << 8) | byte4;
662  return( swapped );
663}
664
665#define CPU_swap_u16( value ) \
666  (((value&0xff) << 8) | ((value >> 8)&0xff))
667
668typedef uint32_t CPU_Counter_ticks;
669
670uint32_t _CPU_Counter_frequency( void );
671
672CPU_Counter_ticks _CPU_Counter_read( void );
673
674static inline CPU_Counter_ticks _CPU_Counter_difference(
675  CPU_Counter_ticks second,
676  CPU_Counter_ticks first
677)
678{
679  return second - first;
680}
681
682/** Type that can store a 32-bit integer or a pointer. */
683typedef uintptr_t CPU_Uint32ptr;
684
685#ifdef __cplusplus
686}
687#endif
688
689#endif
Note: See TracBrowser for help on using the repository browser.