add dev lib

This commit is contained in:
Paul Pan 2021-08-13 20:40:53 +08:00
parent 6fe89863b0
commit eab17474ff
70 changed files with 7450 additions and 1 deletions

View File

@ -15,3 +15,8 @@ indent_style = tab
charset = utf-8 charset = utf-8
indent_style = tab indent_style = tab
indent_size = 8 indent_size = 8
[resources/project/include/*.h]
charset = utf-8
indent_style = tab
indent_size = 8

View File

@ -0,0 +1,61 @@
export LD_PRELOAD =
MEM_DEF = -DMEMSTART=0x80040000 -DMEMSIZE=0x10000
CFLAGS = -O3 -fno-pic -mno-branch-likely -mno-abicalls -msoft-float -fno-builtin -mips1 -I include -EL
AFLAGS = -O2 -fno-pic -mno-abicalls -msoft-float -fno-builtin -mips1 -I include -EL
export CROSS_COMPILE ?= mipsel-linux-gnu-
export MEM_DEF
export CFLAGS
OBJDIR = obj
TARGET = ./src/main.o
all:
mkdir -p $(OBJDIR)
make generate
libtinyc.a :
make -C lib $@
generate: axi_ram.bin convert
./convert axi_ram.bin $(OBJDIR)/
axi_ram.bin: main.elf
${CROSS_COMPILE}objcopy -O binary -j .text -j .data $(OBJDIR)/$< $(OBJDIR)/$@
main.elf: start.o libtinyc.a bin.lds $(TARGET)
${CROSS_COMPILE}ld -g -EL -T bin.lds start.o $(TARGET) lib/libtinyc.a -o $(OBJDIR)/$@
${CROSS_COMPILE}objdump -alD $(OBJDIR)/$@ > $(OBJDIR)/test.s
$(TARGET):
make -C src
bin.lds: bin.lds.S
${CROSS_COMPILE}gcc -EL -E -P -Umips -D_LOADER -U_MAIN $(MEM_DEF) $< -o $@
start.o: start.S
${CROSS_COMPILE}gcc $(CFLAGS) -c $< -nostdinc -nostdlib
convert: convert.c
clang -o convert convert.c
clean:
rm -f *.o *.bin *.elf *.a testbin *.s *.vlog *.coe *.data *.mif
rm -rf obj
make -C lib clean
make -C src clean
reset:
make clean
rm -f bin.lds convert
help:
@echo "####################################################################"
@echo "### help for compiling our awesome project ###"
@echo "####################################################################"
@echo "### options: ###"
@echo "### make : get compiled result, which is saved in ./obj ###"
@echo "### make clean: remove *.o, *.a, and ./obj ###"
@echo "### make reset: "make clean" and remove convert, bin.lds ###"
@echo "### make help : show help information ###"
@echo "####################################################################"

View File

@ -0,0 +1,89 @@
OUTPUT_ARCH(mips)
ENTRY(_start)
SECTIONS
{
/* Read-only sections, merged into text segment: */
. = 0xbfc00000;
.text :
{
_ftext = . ;
*(.text)
rodata_end = .;
} =0
_etext = .;
PROVIDE (etext = .);
.fini : { *(.fini) } =0
.data : AT(rodata_end)
{
*(.rodata*)
*(.reginfo)
*(.init)
*(.stub)
/* .gnu.warning sections are handled specially by elf32.em. */
*(.gnu.warning)
_fdata = . ;
_stack = _fdata + MEMSIZE -32;
*(.data)
*(.data*)
__CTOR_LIST__ = .;
LONG((__CTOR_END__ - __CTOR_LIST__) / 4 - 2)
*(.ctors)
LONG(0)
__CTOR_END__ = .;
__DTOR_LIST__ = .;
LONG((__DTOR_END__ - __DTOR_LIST__) / 4 - 2)
*(.dtors)
LONG(0)
__DTOR_END__ = .;
_gp = ALIGN(16) + 0x7ff0;
*(.got.plt) *(.got)
/* We want the small data sections together, so single-instruction offsets
can access them all, and initialized data all before uninitialized, so
we can shorten the on-disk segment size. */
*(.sdata)
*(.lit8)
*(.lit4)
}
_edata = .;
PROVIDE (edata = .);
data_size = SIZEOF(.data);
data_load_start = LOADADDR(.data);
__bss_start = .;
_fbss = .;
.sbss : { *(.sbss) *(.scommon) }
.bss :
{
*(.dynbss)
*(.bss)
*(COMMON)
}
. = ALIGN(8);
_end = . ;
PROVIDE (end = .);
. = ALIGN(32);
.bigdata : { *(.bigdata) }
. = ALIGN(256);
_heap = . ;
/* These are needed for ELF backends which have not yet been
converted to the new style linker. */
.stab 0 : { *(.stab) }
.stabstr 0 : { *(.stabstr) }
/* DWARF debug sections.
Symbols in the .debug DWARF section are relative to the beginning of the
section so we begin .debug at 0. It's not clear yet what needs to happen
for the others. */
.debug 0 : { *(.debug) }
.debug_srcinfo 0 : { *(.debug_srcinfo) }
.debug_aranges 0 : { *(.debug_aranges) }
.debug_pubnames 0 : { *(.debug_pubnames) }
.debug_sfnames 0 : { *(.debug_sfnames) }
.line 0 : { *(.line) }
/* These must appear regardless of . */
.gptab.sdata : { *(.gptab.data) *(.gptab.sdata) }
.gptab.sbss : { *(.gptab.bss) *(.gptab.sbss) }
.MIPS.abiflags : { *(.MIPS.abiflags) } =0
}

View File

@ -0,0 +1,84 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void binary_out(FILE* out,unsigned char* mem)
{
char tmp;
unsigned char num[8];
num[0] = 1;
num[1] = 2;
num[2] = 4;
num[3] = 8;
num[4] = 16;
num[5] = 32;
num[6] = 64;
num[7] = 128;
for(int i=3;i>=0;i--)
{
for(int j=7;j>=0;j--)
{
if( (mem[i] & num[j] ) != 0)
tmp = '1';
else
tmp = '0';
fprintf(out,"%c",tmp);
}
}
fprintf(out,"\n");
return;
}
int main(int argc, char** argv)
{
FILE *in;
FILE *out;
if(argc < 3){
fprintf(stderr, "Usage: convert main.bin main.data directory\n");
return 1;
}
char str_bin[256];
char str_coe[256], str_mif[256];
strncpy(str_bin, argv[2], 256);
strncpy(str_coe, argv[2], 256);
strncpy(str_mif, argv[2], 256);
strncat(str_bin, argv[1], 256);
strncat(str_coe, "axi_ram.coe", 256);
strncat(str_mif, "axi_ram.mif", 256);
//printf("%s\n%s\n%s\n%s\n%s\n%s\n", str_bin, str_data, str_inst_coe, str_inst_mif, str_data_coe, str_data_mif);
int i,j,k;
unsigned char mem[32];
in = fopen(str_bin, "rb");
out = fopen(str_coe,"w");
fprintf(out, "memory_initialization_radix = 16;\n");
fprintf(out, "memory_initialization_vector =\n");
while(!feof(in)) {
if(fread(mem,1,4,in)!=4) {
fprintf(out, "%02x%02x%02x%02x\n", mem[3], mem[2], mem[1], mem[0]);
break;
}
fprintf(out, "%02x%02x%02x%02x\n", mem[3], mem[2], mem[1],mem[0]);
}
fclose(in);
fclose(out);
in = fopen(str_bin, "rb");
out = fopen(str_mif,"w");
while(!feof(in)) {
if(fread(mem,1,4,in)!=4) {
binary_out(out,mem);
break;
}
binary_out(out,mem);
}
fclose(in);
fclose(out);
return 0;
}

View File

@ -0,0 +1,154 @@
/*
* This file is subject to the terms and conditions of the GNU General Public
* License. See the file "COPYING" in the main directory of this archive
* for more details.
*
* Copyright (C) 1996, 99 Ralf Baechle
* Copyright (C) 2000, 2002 Maciej W. Rozycki
* Copyright (C) 1990, 1999 by Silicon Graphics, Inc.
*/
#ifndef _ASM_ADDRSPACE_H
#define _ASM_ADDRSPACE_H
//#include <spaces.h>
/*
* Configure language
*/
#ifdef __ASSEMBLY__
#define _ATYPE_
#define _ATYPE32_
#define _ATYPE64_
#define _CONST64_(x) x
#else
#define _ATYPE_ __PTRDIFF_TYPE__
#define _ATYPE32_ int
#define _ATYPE64_ __s64
#ifdef CONFIG_64BIT
#define _CONST64_(x) x ## L
#else
#define _CONST64_(x) x ## LL
#endif
#endif
/*
* 32-bit MIPS address spaces
*/
#ifdef __ASSEMBLY__
#define _ACAST32_
#define _ACAST64_
#else
#define _ACAST32_ (_ATYPE_)(_ATYPE32_) /* widen if necessary */
#define _ACAST64_ (_ATYPE64_) /* do _not_ narrow */
#endif
/*
* Returns the kernel segment base of a given address
*/
#define KSEGX(a) ((_ACAST32_ (a)) & 0xe0000000)
/*
* Returns the physical address of a CKSEGx / XKPHYS address
*/
#define CPHYSADDR(a) ((_ACAST32_(a)) & 0x1fffffff)
#define XPHYSADDR(a) ((_ACAST64_(a)) & \
_CONST64_(0x000000ffffffffff))
#ifdef CONFIG_64BIT
/*
* Memory segments (64bit kernel mode addresses)
* The compatibility segments use the full 64-bit sign extended value. Note
* the R8000 doesn't have them so don't reference these in generic MIPS code.
*/
#define XKUSEG _CONST64_(0x0000000000000000)
#define XKSSEG _CONST64_(0x4000000000000000)
#define XKPHYS _CONST64_(0x8000000000000000)
#define XKSEG _CONST64_(0xc000000000000000)
#define CKSEG0 _CONST64_(0xffffffff80000000)
#define CKSEG1 _CONST64_(0xffffffffa0000000)
#define CKSSEG _CONST64_(0xffffffffc0000000)
#define CKSEG3 _CONST64_(0xffffffffe0000000)
#define CKSEG0ADDR(a) (CPHYSADDR(a) | CKSEG0)
#define CKSEG1ADDR(a) (CPHYSADDR(a) | CKSEG1)
#define CKSEG2ADDR(a) (CPHYSADDR(a) | CKSEG2)
#define CKSEG3ADDR(a) (CPHYSADDR(a) | CKSEG3)
#else
#define CKSEG0ADDR(a) (CPHYSADDR(a) | KSEG0)
#define CKSEG1ADDR(a) (CPHYSADDR(a) | KSEG1)
#define CKSEG2ADDR(a) (CPHYSADDR(a) | KSEG2)
#define CKSEG3ADDR(a) (CPHYSADDR(a) | KSEG3)
/*
* Map an address to a certain kernel segment
*/
#define KSEG0ADDR(a) (CPHYSADDR(a) | KSEG0)
#define KSEG1ADDR(a) (CPHYSADDR(a) | KSEG1)
#define KSEG2ADDR(a) (CPHYSADDR(a) | KSEG2)
#define KSEG3ADDR(a) (CPHYSADDR(a) | KSEG3)
/*
* Memory segments (32bit kernel mode addresses)
* These are the traditional names used in the 32-bit universe.
*/
#define KUSEG 0x00000000
#define KSEG0 0x80000000
#define KSEG1 0xa0000000
#define KSEG2 0xc0000000
#define KSEG3 0xe0000000
#define CKUSEG 0x00000000
#define CKSEG0 0x80000000
#define CKSEG1 0xa0000000
#define CKSEG2 0xc0000000
#define CKSEG3 0xe0000000
#endif
/*
* Cache modes for XKPHYS address conversion macros
*/
#define K_CALG_COH_EXCL1_NOL2 0
#define K_CALG_COH_SHRL1_NOL2 1
#define K_CALG_UNCACHED 2
#define K_CALG_NONCOHERENT 3
#define K_CALG_COH_EXCL 4
#define K_CALG_COH_SHAREABLE 5
#define K_CALG_NOTUSED 6
#define K_CALG_UNCACHED_ACCEL 7
/*
* 64-bit address conversions
*/
#define PHYS_TO_XKSEG_UNCACHED(p) PHYS_TO_XKPHYS(K_CALG_UNCACHED, (p))
#define PHYS_TO_XKSEG_CACHED(p) PHYS_TO_XKPHYS(K_CALG_COH_SHAREABLE, (p))
#define XKPHYS_TO_PHYS(p) ((p) & TO_PHYS_MASK)
#define PHYS_TO_XKPHYS(cm, a) (_CONST64_(0x8000000000000000) | \
(_CONST64_(cm) << 59) | (a))
/*
* The ultimate limited of the 64-bit MIPS architecture: 2 bits for selecting
* the region, 3 bits for the CCA mode. This leaves 59 bits of which the
* R8000 implements most with its 48-bit physical address space.
*/
#define TO_PHYS_MASK _CONST64_(0x07ffffffffffffff) /* 2^^59 - 1 */
#ifndef CONFIG_CPU_R8000
/*
* The R8000 doesn't have the 32-bit compat spaces so we don't define them
* in order to catch bugs in the source code.
*/
#define COMPAT_K1BASE32 _CONST64_(0xffffffffa0000000)
#define PHYS_TO_COMPATK1(x) ((x) | COMPAT_K1BASE32) /* 32-bit compat k1 */
#endif
#define KDM_TO_PHYS(x) (_ACAST64_ (x) & TO_PHYS_MASK)
#define PHYS_TO_K0(x) (_ACAST64_ (x) | CAC_BASE)
#endif /* _ASM_ADDRSPACE_H */

View File

@ -0,0 +1,254 @@
/* $OpenBSD: asm.h,v 1.2 1998/03/16 09:03:02 pefo Exp $ */
/*
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Ralph Campbell.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* Copyright (C) 1989 Digital Equipment Corporation.
* Permission to use, copy, modify, and distribute this software and
* its documentation for any purpose and without fee is hereby granted,
* provided that the above copyright notice appears in all copies.
* Digital Equipment Corporation makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*/
#ifndef _MIPS_ASM_H
#define _MIPS_ASM_H
#include <asm/regdef.h>
#ifndef ABICALLS
#define ABICALLS .abicalls
#endif
#if defined(ABICALLS) && !defined(_KERNEL)
ABICALLS
#endif
#define RCSID(x)
/*
* Define how to access unaligned data word
*/
#if defined(__MIPSEL__)
#define LWLO lwl
#define LWHI lwr
#define SWLO swl
#define SWHI swr
#else
#if defined(__MIPSEB__)
#define LWLO lwr
#define LWHI lwl
#define SWLO swr
#define SWHI swl
#else
#error "__MIPSEL__ or __MIPSEB__ must be defined"
#endif
#endif
/*
* Code for setting gp reg if abicalls are used.
*/
#if defined(ABICALLS) && !defined(_KERNEL)
#define ABISETUP \
.set noreorder; \
.cpload t9; \
.set reorder;
#else
#define ABISETUP
#endif
/*
* Define -pg profile entry code.
*/
#if defined(GPROF) || defined(PROF)
#define MCOUNT \
subu sp, sp, 32; \
.cprestore 16; \
sw ra, 28(sp); \
sw gp, 24(sp); \
.set noat; \
.set noreorder; \
move AT, ra; \
jal _mcount; \
subu sp, sp, 8; \
lw ra, 28(sp); \
addu sp, sp, 32; \
.set reorder; \
.set at;
#else
#define MCOUNT
#endif
/*
* LEAF(x)
*
* Declare a leaf routine.
*/
#define LEAF(x) \
.align 3; \
.globl x; \
.ent x, 0; \
x: ; \
.frame sp, 0, ra; \
ABISETUP \
MCOUNT
#define ALEAF(x) \
.globl x; \
x:
/*
* NLEAF(x)
*
* Declare a non-profiled leaf routine.
*/
#define NLEAF(x) \
.align 3; \
.globl x; \
.ent x, 0; \
x: ; \
.frame sp, 0, ra; \
ABISETUP
/*
* NON_LEAF(x)
*
* Declare a non-leaf routine (a routine that makes other C calls).
*/
#define NON_LEAF(x, fsize, retpc) \
.align 3; \
.globl x; \
.ent x, 0; \
x: ; \
.frame sp, fsize, retpc; \
ABISETUP \
MCOUNT
/*
* NNON_LEAF(x)
*
* Declare a non-profiled non-leaf routine
* (a routine that makes other C calls).
*/
#define NNON_LEAF(x, fsize, retpc) \
.align 3; \
.globl x; \
.ent x, 0; \
x: ; \
.frame sp, fsize, retpc \
ABISETUP
/*
* END(x)
*
* Mark end of a procedure.
*/
#define END(x) \
.end x
/*
* Macros to panic and printf from assembly language.
*/
#define PANIC(msg) \
la a0, 9f; \
jal panic; \
MSG(msg)
#define PRINTF(msg) \
la a0, 9f; \
jal printf; \
MSG(msg)
#define MSG(msg) \
.rdata; \
9: .asciiz msg; \
.text
#define ASMSTR(str) \
.asciiz str; \
.align 3
#if (_MIPS_SZPTR == 32)
#define PTR_ADD add
#define PTR_ADDU addu
#define PTR_ADDI addi
#define PTR_ADDIU addiu
#define PTR_SUB sub
#define PTR_SUBU subu
#define PTR_L lw
#define PTR_S sw
#define PTR_LA la
#define PTR_LI li
#define PTR_SLL sll
#define PTR_SLLV sllv
#define PTR_SRL srl
#define PTR_SRLV srlv
#define PTR_SRA sra
#define PTR_SRAV srav
#define PTR_SCALESHIFT 2
#define PTR .word
#define PTRSIZE 4
#define PTRLOG 2
#endif
#if (_MIPS_SZPTR == 64)
#define PTR_ADD dadd
#define PTR_ADDU daddu
#define PTR_ADDI daddi
#define PTR_ADDIU daddiu
#define PTR_SUB dsub
#define PTR_SUBU dsubu
#define PTR_L ld
#define PTR_S sd
#define PTR_LA dla
#define PTR_LI dli
#define PTR_SLL dsll
#define PTR_SLLV dsllv
#define PTR_SRL dsrl
#define PTR_SRLV dsrlv
#define PTR_SRA dsra
#define PTR_SRAV dsrav
#define PTR_SCALESHIFT 3
#define PTR .dword
#define PTRSIZE 8
#define PTRLOG 3
#endif
#endif /* !_MIPS_ASM_H */

View File

@ -0,0 +1,85 @@
/*
* Cache operations for the cache instruction.
*
* This file is subject to the terms and conditions of the GNU General Public
* License. See the file "COPYING" in the main directory of this archive
* for more details.
*
* (C) Copyright 1996, 97, 99, 2002, 03 Ralf Baechle
* (C) Copyright 1999 Silicon Graphics, Inc.
*/
#ifndef __ASM_CACHEOPS_H
#define __ASM_CACHEOPS_H
/*
* Cache Operations available on all MIPS processors with R4000-style caches
*/
#define Index_Invalidate_I 0x00
#define Index_Writeback_Inv_D 0x01
#define Index_Load_Tag_I 0x04
#define Index_Load_Tag_D 0x05
#define Index_Store_Tag_I 0x08
#define Index_Store_Tag_D 0x09
#if defined(CONFIG_CPU_LOONGSON2)
#define Hit_Invalidate_I 0x00
#else
#define Hit_Invalidate_I 0x10
#endif
#define Hit_Invalidate_D 0x11
#define Hit_Writeback_Inv_D 0x15
/*
* R4000-specific cacheops
*/
#define Create_Dirty_Excl_D 0x0d
#define Fill 0x14
#define Hit_Writeback_I 0x18
#define Hit_Writeback_D 0x19
/*
* R4000SC and R4400SC-specific cacheops
*/
#define Index_Invalidate_SI 0x02
#define Index_Writeback_Inv_SD 0x03
#define Index_Load_Tag_SI 0x06
#define Index_Load_Tag_SD 0x07
#define Index_Store_Tag_SI 0x0A
#define Index_Store_Tag_SD 0x0B
#define Create_Dirty_Excl_SD 0x0f
#define Hit_Invalidate_SI 0x12
#define Hit_Invalidate_SD 0x13
#define Hit_Writeback_Inv_SD 0x17
#define Hit_Writeback_SD 0x1b
#define Hit_Set_Virtual_SI 0x1e
#define Hit_Set_Virtual_SD 0x1f
/*
* R5000-specific cacheops
*/
#define R5K_Page_Invalidate_S 0x17
/*
* RM7000-specific cacheops
*/
#define Page_Invalidate_T 0x16
/*
* R10000-specific cacheops
*
* Cacheops 0x02, 0x06, 0x0a, 0x0c-0x0e, 0x16, 0x1a and 0x1e are unused.
* Most of the _S cacheops are identical to the R4000SC _SD cacheops.
*/
#define Index_Writeback_Inv_S 0x03
#define Index_Load_Tag_S 0x07
#define Index_Store_Tag_S 0x0B
#define Hit_Invalidate_S 0x13
#define Cache_Barrier 0x14
#define Hit_Writeback_Inv_S 0x17
#define Index_Load_Data_I 0x18
#define Index_Load_Data_D 0x19
#define Index_Load_Data_S 0x1b
#define Index_Store_Data_I 0x1c
#define Index_Store_Data_D 0x1d
#define Index_Store_Data_S 0x1f
#endif /* __ASM_CACHEOPS_H */

View File

@ -0,0 +1,200 @@
/**************************************************************************
* *
* PROJECT : MIPS port for uC/OS-II *
* *
* MODULE : CONTEXT.h *
* *
* AUTHOR : Michael Anburaj *
* URL : http://geocities.com/michaelanburaj/ *
* EMAIL: michaelanburaj@hotmail.com *
* *
* PROCESSOR : MIPS 4Kc (32 bit RISC) - ATLAS board *
* *
* TOOL-CHAIN : SDE & Cygnus *
* *
* DESCRIPTION : *
* Context switch macros. *
* *
**************************************************************************/
#ifndef __CONTEXT_H__
#define __CONTEXT_H__
/* ********************************************************************* */
/* Module configuration */
/* ********************************************************************* */
/* Interface macro & data definition */
#ifdef __ASSEMBLER__
// push context: at, v0-v1,a0-a3,t0-t9,s0-s7,gp,fp,ra, & pc
#define STORE_REG_RET(Retaddr) \
.set noat; \
.set noreorder; \
subu sp,120; \
sw ra,0(sp); \
sw fp,4(sp); \
sw gp,8(sp); \
sw t9,12(sp); \
sw t8,16(sp); \
sw s7,20(sp); \
sw s6,24(sp); \
sw s5,28(sp); \
sw s4,32(sp); \
sw s3,36(sp); \
sw s2,40(sp); \
sw s1,44(sp); \
sw s0,48(sp); \
sw t7,52(sp); \
sw t6,56(sp); \
sw t5,60(sp); \
sw t4,64(sp); \
sw t3,68(sp); \
sw t2,72(sp); \
sw t1,76(sp); \
sw t0,80(sp); \
sw a3,84(sp); \
sw a2,88(sp); \
sw a1,92(sp); \
sw a0,96(sp); \
sw v1,100(sp); \
sw v0,104(sp); \
sw AT,108(sp); \
mfc0 t0,c0_status; \
sw t0,112(sp); \
sw Retaddr,116(sp); \
.set at
// pop context (normal execution): at, v0-v1,a0-a3,t0-t9,s0-s7,gp,fp,ra, & pc
#define RESTORE_REG_RET() \
.set noat; \
.set noreorder; \
lw ra,0(sp); \
lw fp,4(sp); \
lw gp,8(sp); \
lw t9,12(sp); \
lw t8,16(sp); \
lw s7,20(sp); \
lw s6,24(sp); \
lw s5,28(sp); \
lw s4,32(sp); \
lw s3,36(sp); \
lw s2,40(sp); \
lw s1,44(sp); \
lw s0,48(sp); \
lw t7,52(sp); \
lw t6,56(sp); \
lw t5,60(sp); \
lw t4,64(sp); \
lw t3,68(sp); \
lw t2,72(sp); \
lw t1,76(sp); \
lw t0,80(sp); \
lw a3,84(sp); \
lw a2,88(sp); \
lw a1,92(sp); \
lw a0,96(sp); \
lw v1,100(sp); \
lw v0,104(sp); \
lw AT,108(sp); \
lw k0,112(sp); \
mtc0 k0,c0_status; \
lw k0,116(sp); \
addu sp,120; \
jr k0; \
nop; \
.set at
// pop context: at, v0-v1,a0-a3,t0-t9,s0-s7,gp,fp,ra, & pc
#define RESTORE_REG_ERET() \
.set noat; \
.set noreorder; \
lw ra,0(sp); \
lw fp,4(sp); \
lw gp,8(sp); \
lw t9,12(sp); \
lw t8,16(sp); \
lw s7,20(sp); \
lw s6,24(sp); \
lw s5,28(sp); \
lw s4,32(sp); \
lw s3,36(sp); \
lw s2,40(sp); \
lw s1,44(sp); \
lw s0,48(sp); \
lw t7,52(sp); \
lw t6,56(sp); \
lw t5,60(sp); \
lw t4,64(sp); \
lw t3,68(sp); \
lw t2,72(sp); \
lw t1,76(sp); \
lw t0,80(sp); \
lw a3,84(sp); \
lw a2,88(sp); \
lw a1,92(sp); \
lw a0,96(sp); \
lw v1,100(sp); \
lw v0,104(sp); \
lw AT,108(sp); \
lw k0,112(sp); \
mtc0 k0,c0_status; \
lw k0,116(sp); \
mtc0 k0,c0_epc; \
addu sp,120; \
eret; \
nop; \
.set at
#else
struct pt_regs {
int ra;
int fp;
int gp;
int t9;
int t8;
int s7;
int s6;
int s5;
int s4;
int s3;
int s2;
int s1;
int s0;
int t7;
int t6;
int t5;
int t4;
int t3;
int t2;
int t1;
int t0;
int a3;
int a2;
int a1;
int a0;
int v1;
int v0;
int AT;
int status;
int epc;
};
#endif /* _ASSEMBLER_ */
/* ********************************************************************* */
/* Interface function definition */
/* ********************************************************************* */
#ifdef __cplusplus
}
#endif
#endif /*__CONTEXT_H__*/

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,10 @@
#ifndef _ASM_PAGE_H
#define _ASM_PAGE_H
#include <const.h>
#ifdef CONFIG_PAGE_SIZE_16KB
#define PAGE_SHIFT 14
#endif
#define PAGE_SIZE (_AC(1,UL) << PAGE_SHIFT)
#endif /* _ASM_PAGE_H */

View File

@ -0,0 +1,446 @@
/*
* This file is subject to the terms and conditions of the GNU General Public
* License. See the file "COPYING" in the main directory of this archive
* for more details.
*
* Inline assembly cache operations.
*
* Copyright (C) 1996 David S. Miller (dm@engr.sgi.com)
* Copyright (C) 1997 - 2002 Ralf Baechle (ralf@gnu.org)
* Copyright (C) 2004 Ralf Baechle (ralf@linux-mips.org)
*/
#ifndef _ASM_R4KCACHE_H
#define _ASM_R4KCACHE_H
#include <asm/asm.h>
#include <asm/cacheops.h>
#include <asm/mipsregs.h>
#include <asm/addrspace.h>
#include <asm/page.h>
//#include <asm/cpu-features.h>
//#include <asm/mipsmtregs.h>
#define icache_waysize 0x1000
#define icache_waybit 12
#define icache_ways 4
#define dcache_waysize 0x1000
#define dcache_waybit 12
#define dcache_ways 4
#define dcache_line_size 32
#define icache_line_size 32
#define scache_line_size 32
/*
* This macro return a properly sign-extended address suitable as base address
* for indexed cache operations. Two issues here:
*
* - The MIPS32 and MIPS64 specs permit an implementation to directly derive
* the index bits from the virtual address. This breaks with tradition
* set by the R4000. To keep unpleasant surprises from happening we pick
* an address in KSEG0 / CKSEG0.
* - We need a properly sign extended address for 64-bit code. To get away
* without ifdefs we let the compiler do it by a type cast.
*/
#define INDEX_BASE CKSEG0
#define cache_op(op,addr) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3\n\t \n" \
" cache %0, %1 \n" \
" .set pop \n" \
: \
: "i" (op), "R" (*(unsigned char *)(addr)))
#ifdef CONFIG_MIPS_MT
/*
* Temporary hacks for SMTC debug. Optionally force single-threaded
* execution during I-cache flushes.
*/
#define PROTECT_CACHE_FLUSHES 1
#ifdef PROTECT_CACHE_FLUSHES
extern int mt_protiflush;
extern int mt_protdflush;
extern void mt_cflush_lockdown(void);
extern void mt_cflush_release(void);
#define BEGIN_MT_IPROT \
unsigned long flags = 0; \
unsigned long mtflags = 0; \
if(mt_protiflush) { \
local_irq_save(flags); \
ehb(); \
mtflags = dvpe(); \
mt_cflush_lockdown(); \
}
#define END_MT_IPROT \
if(mt_protiflush) { \
mt_cflush_release(); \
evpe(mtflags); \
local_irq_restore(flags); \
}
#define BEGIN_MT_DPROT \
unsigned long flags = 0; \
unsigned long mtflags = 0; \
if(mt_protdflush) { \
local_irq_save(flags); \
ehb(); \
mtflags = dvpe(); \
mt_cflush_lockdown(); \
}
#define END_MT_DPROT \
if(mt_protdflush) { \
mt_cflush_release(); \
evpe(mtflags); \
local_irq_restore(flags); \
}
#else
#define BEGIN_MT_IPROT
#define BEGIN_MT_DPROT
#define END_MT_IPROT
#define END_MT_DPROT
#endif /* PROTECT_CACHE_FLUSHES */
#define __iflush_prologue \
unsigned long redundance; \
extern int mt_n_iflushes; \
BEGIN_MT_IPROT \
for (redundance = 0; redundance < mt_n_iflushes; redundance++) {
#define __iflush_epilogue \
END_MT_IPROT \
}
#define __dflush_prologue \
unsigned long redundance; \
extern int mt_n_dflushes; \
BEGIN_MT_DPROT \
for (redundance = 0; redundance < mt_n_dflushes; redundance++) {
#define __dflush_epilogue \
END_MT_DPROT \
}
#define __inv_dflush_prologue __dflush_prologue
#define __inv_dflush_epilogue __dflush_epilogue
#define __sflush_prologue {
#define __sflush_epilogue }
#define __inv_sflush_prologue __sflush_prologue
#define __inv_sflush_epilogue __sflush_epilogue
#else /* CONFIG_MIPS_MT */
#define __iflush_prologue {
#define __iflush_epilogue }
#define __dflush_prologue {
#define __dflush_epilogue }
#define __inv_dflush_prologue {
#define __inv_dflush_epilogue }
#define __sflush_prologue {
#define __sflush_epilogue }
#define __inv_sflush_prologue {
#define __inv_sflush_epilogue }
#endif /* CONFIG_MIPS_MT */
static inline void flush_icache_line_indexed(unsigned long addr)
{
__iflush_prologue
cache_op(Index_Invalidate_I, addr);
__iflush_epilogue
}
static inline void flush_dcache_line_indexed(unsigned long addr)
{
__dflush_prologue
cache_op(Index_Writeback_Inv_D, addr);
__dflush_epilogue
}
static inline void flush_scache_line_indexed(unsigned long addr)
{
cache_op(Index_Writeback_Inv_SD, addr);
}
static inline void flush_icache_line(unsigned long addr)
{
__iflush_prologue
cache_op(Hit_Invalidate_I, addr);
__iflush_epilogue
}
static inline void flush_dcache_line(unsigned long addr)
{
__dflush_prologue
cache_op(Hit_Writeback_Inv_D, addr);
__dflush_epilogue
}
static inline void invalidate_dcache_line(unsigned long addr)
{
__dflush_prologue
cache_op(Hit_Invalidate_D, addr);
__dflush_epilogue
}
static inline void invalidate_scache_line(unsigned long addr)
{
cache_op(Hit_Invalidate_SD, addr);
}
static inline void flush_scache_line(unsigned long addr)
{
cache_op(Hit_Writeback_Inv_SD, addr);
}
#define protected_cache_op(op,addr) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3 \n" \
"1: cache %0, (%1) \n" \
"2: .set pop \n" \
: \
: "i" (op), "r" (addr))
/*
* The next two are for badland addresses like signal trampolines.
*/
static inline void protected_flush_icache_line(unsigned long addr)
{
protected_cache_op(Hit_Invalidate_I, addr);
}
/*
* R10000 / R12000 hazard - these processors don't support the Hit_Writeback_D
* cacheop so we use Hit_Writeback_Inv_D which is supported by all R4000-style
* caches. We're talking about one cacheline unnecessarily getting invalidated
* here so the penalty isn't overly hard.
*/
static inline void protected_writeback_dcache_line(unsigned long addr)
{
protected_cache_op(Hit_Writeback_Inv_D, addr);
}
static inline void protected_writeback_scache_line(unsigned long addr)
{
protected_cache_op(Hit_Writeback_Inv_SD, addr);
}
/*
* This one is RM7000-specific
*/
static inline void invalidate_tcache_page(unsigned long addr)
{
cache_op(Page_Invalidate_T, addr);
}
#define cache16_unroll32(base,op) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3 \n" \
" cache %1, 0x000(%0); cache %1, 0x010(%0) \n" \
" cache %1, 0x020(%0); cache %1, 0x030(%0) \n" \
" cache %1, 0x040(%0); cache %1, 0x050(%0) \n" \
" cache %1, 0x060(%0); cache %1, 0x070(%0) \n" \
" cache %1, 0x080(%0); cache %1, 0x090(%0) \n" \
" cache %1, 0x0a0(%0); cache %1, 0x0b0(%0) \n" \
" cache %1, 0x0c0(%0); cache %1, 0x0d0(%0) \n" \
" cache %1, 0x0e0(%0); cache %1, 0x0f0(%0) \n" \
" cache %1, 0x100(%0); cache %1, 0x110(%0) \n" \
" cache %1, 0x120(%0); cache %1, 0x130(%0) \n" \
" cache %1, 0x140(%0); cache %1, 0x150(%0) \n" \
" cache %1, 0x160(%0); cache %1, 0x170(%0) \n" \
" cache %1, 0x180(%0); cache %1, 0x190(%0) \n" \
" cache %1, 0x1a0(%0); cache %1, 0x1b0(%0) \n" \
" cache %1, 0x1c0(%0); cache %1, 0x1d0(%0) \n" \
" cache %1, 0x1e0(%0); cache %1, 0x1f0(%0) \n" \
" .set pop \n" \
: \
: "r" (base), \
"i" (op));
#define cache32_unroll32(base,op) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3 \n" \
" cache %1, 0x000(%0); cache %1, 0x020(%0) \n" \
" cache %1, 0x040(%0); cache %1, 0x060(%0) \n" \
" cache %1, 0x080(%0); cache %1, 0x0a0(%0) \n" \
" cache %1, 0x0c0(%0); cache %1, 0x0e0(%0) \n" \
" cache %1, 0x100(%0); cache %1, 0x120(%0) \n" \
" cache %1, 0x140(%0); cache %1, 0x160(%0) \n" \
" cache %1, 0x180(%0); cache %1, 0x1a0(%0) \n" \
" cache %1, 0x1c0(%0); cache %1, 0x1e0(%0) \n" \
" cache %1, 0x200(%0); cache %1, 0x220(%0) \n" \
" cache %1, 0x240(%0); cache %1, 0x260(%0) \n" \
" cache %1, 0x280(%0); cache %1, 0x2a0(%0) \n" \
" cache %1, 0x2c0(%0); cache %1, 0x2e0(%0) \n" \
" cache %1, 0x300(%0); cache %1, 0x320(%0) \n" \
" cache %1, 0x340(%0); cache %1, 0x360(%0) \n" \
" cache %1, 0x380(%0); cache %1, 0x3a0(%0) \n" \
" cache %1, 0x3c0(%0); cache %1, 0x3e0(%0) \n" \
" .set pop \n" \
: \
: "r" (base), \
"i" (op));
#define cache64_unroll32(base,op) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3 \n" \
" cache %1, 0x000(%0); cache %1, 0x040(%0) \n" \
" cache %1, 0x080(%0); cache %1, 0x0c0(%0) \n" \
" cache %1, 0x100(%0); cache %1, 0x140(%0) \n" \
" cache %1, 0x180(%0); cache %1, 0x1c0(%0) \n" \
" cache %1, 0x200(%0); cache %1, 0x240(%0) \n" \
" cache %1, 0x280(%0); cache %1, 0x2c0(%0) \n" \
" cache %1, 0x300(%0); cache %1, 0x340(%0) \n" \
" cache %1, 0x380(%0); cache %1, 0x3c0(%0) \n" \
" cache %1, 0x400(%0); cache %1, 0x440(%0) \n" \
" cache %1, 0x480(%0); cache %1, 0x4c0(%0) \n" \
" cache %1, 0x500(%0); cache %1, 0x540(%0) \n" \
" cache %1, 0x580(%0); cache %1, 0x5c0(%0) \n" \
" cache %1, 0x600(%0); cache %1, 0x640(%0) \n" \
" cache %1, 0x680(%0); cache %1, 0x6c0(%0) \n" \
" cache %1, 0x700(%0); cache %1, 0x740(%0) \n" \
" cache %1, 0x780(%0); cache %1, 0x7c0(%0) \n" \
" .set pop \n" \
: \
: "r" (base), \
"i" (op));
#define cache128_unroll32(base,op) \
__asm__ __volatile__( \
" .set push \n" \
" .set noreorder \n" \
" .set mips3 \n" \
" cache %1, 0x000(%0); cache %1, 0x080(%0) \n" \
" cache %1, 0x100(%0); cache %1, 0x180(%0) \n" \
" cache %1, 0x200(%0); cache %1, 0x280(%0) \n" \
" cache %1, 0x300(%0); cache %1, 0x380(%0) \n" \
" cache %1, 0x400(%0); cache %1, 0x480(%0) \n" \
" cache %1, 0x500(%0); cache %1, 0x580(%0) \n" \
" cache %1, 0x600(%0); cache %1, 0x680(%0) \n" \
" cache %1, 0x700(%0); cache %1, 0x780(%0) \n" \
" cache %1, 0x800(%0); cache %1, 0x880(%0) \n" \
" cache %1, 0x900(%0); cache %1, 0x980(%0) \n" \
" cache %1, 0xa00(%0); cache %1, 0xa80(%0) \n" \
" cache %1, 0xb00(%0); cache %1, 0xb80(%0) \n" \
" cache %1, 0xc00(%0); cache %1, 0xc80(%0) \n" \
" cache %1, 0xd00(%0); cache %1, 0xd80(%0) \n" \
" cache %1, 0xe00(%0); cache %1, 0xe80(%0) \n" \
" cache %1, 0xf00(%0); cache %1, 0xf80(%0) \n" \
" .set pop \n" \
: \
: "r" (base), \
"i" (op));
/* build blast_xxx, blast_xxx_page, blast_xxx_page_indexed */
#define __BUILD_BLAST_CACHE(pfx, desc, indexop, hitop, lsize) \
static inline void blast_##pfx##cache##lsize(void) \
{ \
unsigned long start = INDEX_BASE; \
unsigned long end = start + desc##_##waysize; \
unsigned long ws_inc = 1UL << desc##_##waybit; \
unsigned long ws_end = desc##_##ways << \
desc##_##waybit; \
unsigned long ws, addr; \
\
__##pfx##flush_prologue \
\
for (ws = 0; ws < ws_end; ws += ws_inc) \
for (addr = start; addr < end; addr += lsize * 32) \
cache##lsize##_unroll32(addr|ws, indexop); \
\
__##pfx##flush_epilogue \
} \
\
static inline void blast_##pfx##cache##lsize##_page(unsigned long page) \
{ \
unsigned long start = page; \
unsigned long end = page + PAGE_SIZE; \
\
__##pfx##flush_prologue \
\
do { \
cache##lsize##_unroll32(start, hitop); \
start += lsize * 32; \
} while (start < end); \
\
__##pfx##flush_epilogue \
} \
\
static inline void blast_##pfx##cache##lsize##_page_indexed(unsigned long page) \
{ \
unsigned long indexmask = desc##_##waysize - 1; \
unsigned long start = INDEX_BASE + (page & indexmask); \
unsigned long end = start + PAGE_SIZE; \
unsigned long ws_inc = 1UL << desc##_##waybit; \
unsigned long ws_end = desc##_##ways << \
desc##_##waybit; \
unsigned long ws, addr; \
\
__##pfx##flush_prologue \
\
for (ws = 0; ws < ws_end; ws += ws_inc) \
for (addr = start; addr < end; addr += lsize * 32) \
cache##lsize##_unroll32(addr|ws, indexop); \
\
__##pfx##flush_epilogue \
}
__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 16)
__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 16)
__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 32)
__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 32)
__BUILD_BLAST_CACHE(d, dcache, Index_Writeback_Inv_D, Hit_Writeback_Inv_D, 64)
__BUILD_BLAST_CACHE(i, icache, Index_Invalidate_I, Hit_Invalidate_I, 64)
__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 16)
__BUILD_BLAST_CACHE(inv_d, dcache, Index_Writeback_Inv_D, Hit_Invalidate_D, 32)
/* build blast_xxx_range, protected_blast_xxx_range */
#define __BUILD_BLAST_CACHE_RANGE(pfx, desc, hitop, prot) \
static inline void prot##blast_##pfx##cache##_range(unsigned long start, \
unsigned long end) \
{ \
unsigned long lsize = desc##_line_size; \
unsigned long addr = start & ~(lsize - 1); \
unsigned long aend = (end - 1) & ~(lsize - 1); \
\
__##pfx##flush_prologue \
\
while (1) { \
prot##cache_op(hitop, addr); \
if (addr == aend) \
break; \
addr += lsize; \
} \
\
__##pfx##flush_epilogue \
}
__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, protected_)
__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, protected_)
__BUILD_BLAST_CACHE_RANGE(i, icache, Hit_Invalidate_I, protected_)
__BUILD_BLAST_CACHE_RANGE(d, dcache, Hit_Writeback_Inv_D, )
__BUILD_BLAST_CACHE_RANGE(s, scache, Hit_Writeback_Inv_SD, )
/* blast_inv_dcache_range */
__BUILD_BLAST_CACHE_RANGE(inv_d, dcache, Hit_Invalidate_D, )
__BUILD_BLAST_CACHE_RANGE(inv_s, scache, Hit_Invalidate_SD, )
#endif /* _ASM_R4KCACHE_H */

View File

@ -0,0 +1,113 @@
/* $OpenBSD: regdef.h,v 1.3 1999/01/27 04:46:06 imp Exp $ */
/*
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Ralph Campbell. This file is derived from the MIPS RISC
* Architecture book by Gerry Kane.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* @(#)regdef.h 8.1 (Berkeley) 6/10/93
*/
#ifndef _MIPS_REGDEF_H_
#define _MIPS_REGDEF_H_
#define zero $0 /* always zero */
#define AT $at /* assembler temp */
#define v0 $2 /* return value */
#define v1 $3
#define a0 $4 /* argument registers */
#define a1 $5
#define a2 $6
#define a3 $7
#define t0 $8 /* temp registers (not saved across subroutine calls) */
#define t1 $9
#define t2 $10
#define t3 $11
#define t4 $12
#define t5 $13
#define t6 $14
#define t7 $15
#define s0 $16 /* saved across subroutine calls (callee saved) */
#define s1 $17
#define s2 $18
#define s3 $19
#define s4 $20
#define s5 $21
#define s6 $22
#define s7 $23
#define t8 $24 /* two more temp registers */
#define t9 $25
#define k0 $26 /* kernel temporary */
#define k1 $27
#define gp $28 /* global pointer */
#define sp $29 /* stack pointer */
#define s8 $30 /* one more callee saved */
#define ra $31 /* return address */
#define fp $30
#define c0_index $0
#define c0_random $1
#define c0_entrylo0 $2
#define c0_entrylo1 $3
#define c0_conf $3
#define c0_context $4
#define c0_pagemask $5
#define c0_wired $6
#define c0_info $7
#define c0_badvaddr $8
#define c0_count $9
#define c0_entryhi $10
#define c0_compare $11
#define c0_status $12
#define c0_cause $13
#define c0_epc $14
#define c0_prid $15
#define c0_config $16
#define c0_lladdr $17
#define c0_watchlo $18
#define c0_watchhi $19
#define c0_xcontext $20
#define c0_framemask $21
#define c0_diagnostic $22
#define c0_debug $23
#define c0_depc $24
#define c0_performance $25
#define c0_ecc $26
#define c0_cacheerr $27
#define c0_taglo $28
#define c0_taghi $29
#define c0_errorepc $30
#define c0_desave $31
#endif /* !_MIPS_REGDEF_H_ */

View File

@ -0,0 +1,14 @@
#ifndef __CMDLINE_H__
#define __CMDLINE_H__
typedef struct cmd_struct {
const char *cmdname;
int (*func)(int, void *[]);
int repeat;
const char *usage;
const char *expression;
} cmdline_t;
#define V_NUM 8 //the number of argv
#define V_LEN 15 //the length of argv
#define CMD_BUFF 64
#endif

View File

@ -0,0 +1,180 @@
#ifndef COMMON_H
#define COMMON_H
#define SERIAL 0xffffffffff2001e0
#ifndef __ASSEMBLER__
typedef void * va_list;
#if __GNUC__<3 || (__GNUC__==3 && __GNUC_MINOR__<3)
#define va_start(ap,fmt) ap=((void *)&fmt)+1;
#else
#define va_start __builtin_va_start
#endif
#define va_arg __builtin_va_arg
#define va_end __builtin_va_end
#define __P(x) x
typedef unsigned int u_int;
typedef unsigned long u_long;
typedef unsigned int uint32_t;
typedef unsigned int size_t;
#define isdigit(c) (c>='0' && c<='9')
#define FMT_RJUST 0
#define FMT_LJUST 1
#define FMT_RJUST0 2
#define FMT_CENTER 3
#define __read_32bit_c0_register(source, sel) \
({ int __res; \
if (sel == 0) \
__asm__ __volatile__( \
"mfc0\t%0, " #source "\n\t" \
: "=r" (__res)); \
else \
__asm__ __volatile__( \
".set\tmips32\n\t" \
"mfc0\t%0, " #source ", " #sel "\n\t" \
".set\tmips0\n\t" \
: "=r" (__res)); \
__res; \
})
#define __write_32bit_c0_register(register, sel, value) \
do { \
if (sel == 0) \
__asm__ __volatile__( \
"mtc0\t%z0, " #register "\n\t" \
: : "Jr" ((unsigned int)(value))); \
else \
__asm__ __volatile__( \
".set\tmips32\n\t" \
"mtc0\t%z0, " #register ", " #sel "\n\t" \
".set\tmips0" \
: : "Jr" ((unsigned int)(value))); \
} while (0)
#define read_c0_index() __read_32bit_c0_register($0, 0)
#define write_c0_index(val) __write_32bit_c0_register($0, 0, val)
#define read_c0_entrylo0() __read_ulong_c0_register($2, 0)
#define write_c0_entrylo0(val) __write_ulong_c0_register($2, 0, val)
#define read_c0_entrylo1() __read_ulong_c0_register($3, 0)
#define write_c0_entrylo1(val) __write_ulong_c0_register($3, 0, val)
#define read_c0_conf() __read_32bit_c0_register($3, 0)
#define write_c0_conf(val) __write_32bit_c0_register($3, 0, val)
#define read_c0_context() __read_ulong_c0_register($4, 0)
#define write_c0_context(val) __write_ulong_c0_register($4, 0, val)
#define read_c0_pagemask() __read_32bit_c0_register($5, 0)
#define write_c0_pagemask(val) __write_32bit_c0_register($5, 0, val)
#define read_c0_wired() __read_32bit_c0_register($6, 0)
#define write_c0_wired(val) __write_32bit_c0_register($6, 0, val)
#define read_c0_info() __read_32bit_c0_register($7, 0)
#define read_c0_cache() __read_32bit_c0_register($7, 0) /* TX39xx */
#define write_c0_cache(val) __write_32bit_c0_register($7, 0, val)
#define read_c0_badvaddr() __read_ulong_c0_register($8, 0)
#define write_c0_badvaddr(val) __write_ulong_c0_register($8, 0, val)
#define read_c0_count() __read_32bit_c0_register($9, 0)
#define write_c0_count(val) __write_32bit_c0_register($9, 0, val)
#define read_c0_count2() __read_32bit_c0_register($9, 6) /* pnx8550 */
#define write_c0_count2(val) __write_32bit_c0_register($9, 6, val)
#define read_c0_count3() __read_32bit_c0_register($9, 7) /* pnx8550 */
#define write_c0_count3(val) __write_32bit_c0_register($9, 7, val)
#define read_c0_entryhi() __read_ulong_c0_register($10, 0)
#define write_c0_entryhi(val) __write_ulong_c0_register($10, 0, val)
#define read_c0_compare() __read_32bit_c0_register($11, 0)
#define write_c0_compare(val) __write_32bit_c0_register($11, 0, val)
#define read_c0_compare2() __read_32bit_c0_register($11, 6) /* pnx8550 */
#define write_c0_compare2(val) __write_32bit_c0_register($11, 6, val)
#define read_c0_compare3() __read_32bit_c0_register($11, 7) /* pnx8550 */
#define write_c0_compare3(val) __write_32bit_c0_register($11, 7, val)
#define read_c0_status() __read_32bit_c0_register($12, 0)
#define write_c0_status(val) __write_32bit_c0_register($12, 0, val)
#define read_c0_cause() __read_32bit_c0_register($13, 0)
#define write_c0_cause(val) __write_32bit_c0_register($13, 0, val)
#define read_c0_epc() __read_ulong_c0_register($14, 0)
#define write_c0_epc(val) __write_ulong_c0_register($14, 0, val)
#define read_c0_prid() __read_32bit_c0_register($15, 0)
#define read_c0_config() __read_32bit_c0_register($16, 0)
#define read_c0_config1() __read_32bit_c0_register($16, 1)
#define read_c0_config2() __read_32bit_c0_register($16, 2)
#define read_c0_config3() __read_32bit_c0_register($16, 3)
#define read_c0_config4() __read_32bit_c0_register($16, 4)
#define read_c0_config5() __read_32bit_c0_register($16, 5)
#define read_c0_config6() __read_32bit_c0_register($16, 6)
#define read_c0_config7() __read_32bit_c0_register($16, 7)
#define write_c0_config(val) __write_32bit_c0_register($16, 0, val)
#define write_c0_config1(val) __write_32bit_c0_register($16, 1, val)
#define write_c0_config2(val) __write_32bit_c0_register($16, 2, val)
#define write_c0_config3(val) __write_32bit_c0_register($16, 3, val)
#define write_c0_config4(val) __write_32bit_c0_register($16, 4, val)
#define write_c0_config5(val) __write_32bit_c0_register($16, 5, val)
#define write_c0_config6(val) __write_32bit_c0_register($16, 6, val)
#define write_c0_config7(val) __write_32bit_c0_register($16, 7, val)
/*
* The WatchLo register. There may be upto 8 of them.
*/
#define read_c0_watchlo0() __read_ulong_c0_register($18, 0)
#define read_c0_watchlo1() __read_ulong_c0_register($18, 1)
#define read_c0_watchlo2() __read_ulong_c0_register($18, 2)
#define read_c0_watchlo3() __read_ulong_c0_register($18, 3)
#define read_c0_watchlo4() __read_ulong_c0_register($18, 4)
#define read_c0_watchlo5() __read_ulong_c0_register($18, 5)
#define read_c0_watchlo6() __read_ulong_c0_register($18, 6)
#define read_c0_watchlo7() __read_ulong_c0_register($18, 7)
#define write_c0_watchlo0(val) __write_ulong_c0_register($18, 0, val)
#define write_c0_watchlo1(val) __write_ulong_c0_register($18, 1, val)
#define write_c0_watchlo2(val) __write_ulong_c0_register($18, 2, val)
#define write_c0_watchlo3(val) __write_ulong_c0_register($18, 3, val)
#define write_c0_watchlo4(val) __write_ulong_c0_register($18, 4, val)
#define write_c0_watchlo5(val) __write_ulong_c0_register($18, 5, val)
#define write_c0_watchlo6(val) __write_ulong_c0_register($18, 6, val)
#define write_c0_watchlo7(val) __write_ulong_c0_register($18, 7, val)
/*
* The WatchHi register. There may be upto 8 of them.
*/
#define read_c0_watchhi0() __read_32bit_c0_register($19, 0)
#define read_c0_watchhi1() __read_32bit_c0_register($19, 1)
#define read_c0_watchhi2() __read_32bit_c0_register($19, 2)
#define read_c0_watchhi3() __read_32bit_c0_register($19, 3)
#define read_c0_watchhi4() __read_32bit_c0_register($19, 4)
#define read_c0_watchhi5() __read_32bit_c0_register($19, 5)
#define read_c0_watchhi6() __read_32bit_c0_register($19, 6)
#define read_c0_watchhi7() __read_32bit_c0_register($19, 7)
#define write_c0_watchhi0(val) __write_32bit_c0_register($19, 0, val)
#define write_c0_watchhi1(val) __write_32bit_c0_register($19, 1, val)
#define write_c0_watchhi2(val) __write_32bit_c0_register($19, 2, val)
#define write_c0_watchhi3(val) __write_32bit_c0_register($19, 3, val)
#define write_c0_watchhi4(val) __write_32bit_c0_register($19, 4, val)
#define write_c0_watchhi5(val) __write_32bit_c0_register($19, 5, val)
#define write_c0_watchhi6(val) __write_32bit_c0_register($19, 6, val)
#define write_c0_watchhi7(val) __write_32bit_c0_register($19, 7, val)
#endif
#endif

View File

@ -0,0 +1,24 @@
/* const.h: Macros for dealing with constants. */
#ifndef _LINUX_CONST_H
#define _LINUX_CONST_H
/* Some constant macros are used in both assembler and
* C code. Therefore we cannot annotate them always with
* 'UL' and other type specifiers unilaterally. We
* use the following macros to deal with this.
*
* Similarly, _AT() will cast an expression with a type in C, but
* leave it unchanged in asm.
*/
#ifdef __ASSEMBLY__
#define _AC(X,Y) X
#define _AT(T,X) X
#else
#define __AC(X,Y) (X##Y)
#define _AC(X,Y) __AC(X,Y)
#define _AT(T,X) ((T)(X))
#endif
#endif /* !(_LINUX_CONST_H) */

View File

@ -0,0 +1,5 @@
#ifndef __CPU_H_
#define __CPU_H_
#define SR_BOOT_EXC_VEC 0x00400000
#define PG_SIZE_4K 0x00000000
#endif

View File

@ -0,0 +1,105 @@
//soc confreg
#define CONFREG_NULL 0xbfaf8ffc
#define CONFREG_CR0 0xbfaf8000
#define CONFREG_CR1 0xbfaf8004
#define CONFREG_CR2 0xbfaf8008
#define CONFREG_CR3 0xbfaf800c
#define CONFREG_CR4 0xbfaf8010
#define CONFREG_CR5 0xbfaf8014
#define CONFREG_CR6 0xbfaf8018
#define CONFREG_CR7 0xbfaf801c
#define UART_ADDR 0xbfaffff0
#define SIMU_FLAG_ADDR 0xbfaffff4
#define OPEN_TRACE_ADDR 0xbfaffff8
#define NUM_MONITOR_ADDR 0xbfaffffc
#define LED_ADDR 0xbfaff000
#define LED_RG0_ADDR 0xbfaff004
#define LED_RG1_ADDR 0xbfaff008
#define NUM_ADDR 0xbfaff010
#define SWITCH_ADDR 0xbfaff020
#define BTN_KEY_ADDR 0xbfaff024
#define BTN_STEP_ADDR 0xbfaff028
#define TIMER_ADDR 0xbfafe000
#define SOC_LED (* (volatile unsigned *) LED_ADDR )
#define SOC_LED_RG0 (* (volatile unsigned *) LED_RG0_ADDR )
#define SOC_LED_RG1 (* (volatile unsigned *) LED_RG1_ADDR )
#define SOC_NUM (* (volatile unsigned *) NUM_ADDR )
#define SOC_SWITCHE (* (volatile unsigned *) SWITCH_ADDR )
#define SOC_BTN_KEY (* (volatile unsigned *) BTN_KEY_ADDR )
#define SOC_BTN_STEP (* (volatile unsigned *) BTN_STEP_ADDR )
#define SOC_TIMER (* (volatile unsigned *) TIMER_ADDR )
//#define disable_trace_cmp *((volatile int *)OPEN_TRACE_ADDR) = 0; \
// *((volatile int *)CONFREG_NULL ) = 0; \
// *((volatile int *)CONFREG_NULL ) = 0
//#define enable_trace_cmp *((volatile int *)OPEN_TRACE_ADDR) = 1; \
// *((volatile int *)CONFREG_NULL ) = 0; \
*((volatile int *)CONFREG_NULL ) = 0
#define trace_cmp_flag (*((volatile int *)OPEN_TRACE_ADDR))
#define disable_trace_cmp asm volatile( \
".set noreorder;" \
"lui $25,0xbfb0\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $0,-0x8($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"lw $0,-0x7004($25)\n\t" \
"lw $25,-0x8($25)\n\t" \
".set reorder" \
:::"$25" \
)
#define disable_trace_cmp_s .set noreorder; \
lui k1,0xbfb0; \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
sw $0,-0x8(k1); \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
lw $0,-0x7004(k1); \
lw k1,-0x8(k1); \
.set reorder; \
#define disable_num_monitor_s .set noreorder; \
lui k1,0xbfb0; \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
sw $0,-0x4(k1); \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
lw $0,-0x7004(k1); \
lw k1,-0x4(k1); \
.set reorder; \
#define enable_trace_cmp asm volatile( \
".set noreorder;" \
"lui $25,0xbfb0\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $25,-8($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"sw $0,-0x7004($25)\n\t" \
"lw $0,-0x7004($25)\n\t" \
"lw $25,-0x8($25)\n\t" \
".set reorder" \
:::"$25" \
)
#define enable_trace_cmp_s .set noreorder; \
lui k1,0xbfb0; \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
sw k1,-8(k1); \
sw $0,-0x7004(k1); \
sw $0,-0x7004(k1); \
lw $0,-0x7004(k1); \
lw k1,-0x8(k1); \
.set reorder; \
#define write_confreg_cr(num,data) *((volatile int *)(CONFREG_CR0+4*num)) = data
#define read_confreg_cr(num,data) data=*((volatile int *)(CONFREG_CR0+4*num))
#define NOP addu zero, zero, zero
#define LI(reg, imm) \
li reg, imm

View File

@ -0,0 +1,39 @@
#ifndef _ASM_GENERIC_ERRNO_BASE_H
#define _ASM_GENERIC_ERRNO_BASE_H
#define EPERM 1 /* Operation not permitted */
#define ENOENT 2 /* No such file or directory */
#define ESRCH 3 /* No such process */
#define EINTR 4 /* Interrupted system call */
#define EIO 5 /* I/O error */
#define ENXIO 6 /* No such device or address */
#define E2BIG 7 /* Argument list too long */
#define ENOEXEC 8 /* Exec format error */
#define EBADF 9 /* Bad file number */
#define ECHILD 10 /* No child processes */
#define EAGAIN 11 /* Try again */
#define ENOMEM 12 /* Out of memory */
#define EACCES 13 /* Permission denied */
#define EFAULT 14 /* Bad address */
#define ENOTBLK 15 /* Block device required */
#define EBUSY 16 /* Device or resource busy */
#define EEXIST 17 /* File exists */
#define EXDEV 18 /* Cross-device link */
#define ENODEV 19 /* No such device */
#define ENOTDIR 20 /* Not a directory */
#define EISDIR 21 /* Is a directory */
#define EINVAL 22 /* Invalid argument */
#define ENFILE 23 /* File table overflow */
#define EMFILE 24 /* Too many open files */
#define ENOTTY 25 /* Not a typewriter */
#define ETXTBSY 26 /* Text file busy */
#define EFBIG 27 /* File too large */
#define ENOSPC 28 /* No space left on device */
#define ESPIPE 29 /* Illegal seek */
#define EROFS 30 /* Read-only file system */
#define EMLINK 31 /* Too many links */
#define EPIPE 32 /* Broken pipe */
#define EDOM 33 /* Math argument out of domain of func */
#define ERANGE 34 /* Math result not representable */
#endif

View File

@ -0,0 +1,73 @@
#ifndef MYREGS_H
#define MYREGS_H
#define IRQF_SHARED 0x00000080
#define SA_SHIRQ IRQF_SHARED
#define IRQF_TRIGGER_NONE 0x00000000
#define IRQF_TRIGGER_RISING 0x00000001
#define IRQF_TRIGGER_FALLING 0x00000002
#define IRQF_TRIGGER_HIGH 0x00000004
#define IRQF_TRIGGER_LOW 0x00000008
#define IRQF_TRIGGER_MASK (IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING | IRQF_TRIGGER_HIGH | IRQF_TRIGGER_LOW)
#define IRQF_TRIGGER_PROBE 0x00000010
struct sb2f_board_intc_regs
{
volatile unsigned int int_isr;
volatile unsigned int int_en;
volatile unsigned int int_set;
volatile unsigned int int_clr;
volatile unsigned int int_pol;
volatile unsigned int int_edge;
};
static struct sb2f_board_intc_regs volatile *sb2f_board_hw0_icregs = (struct sb2f_board_intc_regs volatile*)0xbfd01040;
struct irq_desc;
typedef void (*irq_flow_handler_t)(unsigned int irq,struct irq_desc *desc);
typedef int (*irq_handler_t)(void *);
struct irq_chip{
char *name;
unsigned int (*startup)(unsigned int irq);
unsigned int (*shutdown)(unsigned int irq);
unsigned int (*enable)(unsigned int irq);
unsigned int (*disable)(unsigned int irq);
unsigned int (*ack)(unsigned int irq);
unsigned int (*mask)(unsigned int irq);
unsigned int (*mask_ack)(unsigned int irq);
unsigned int (*unmask)(unsigned int irq);
unsigned int (*eoi)(unsigned int irq);
void (*end)(unsigned int irq);
int (*set_type)(unsigned int irq,unsigned int flow_type);
};
struct irqaction{
irq_handler_t handler;
unsigned long flags;
const char* name;
struct irqaction *next;
int irq;
void *dev_id;
};
struct irq_desc{
irq_flow_handler_t handle_irq;
struct irq_chip *chip;
struct irqaction *action;
};
static inline int fls(int word)
{
__asm__(".set mips32");
__asm__("clz %0, %1" : "=r" (word) : "r" (word));
__asm__(".set mips0");
return 32-word;
}
static int inline ffs(int word)
{
if(!word)
return 0;
return fls(word & -word);
}
int request_irq(unsigned int irq, irq_handler_t handler, unsigned long irqflags,const char *devname, void *dev_id);
#define IRQ_RETVAL(x) ((x) != 0)
#endif

View File

@ -0,0 +1,4 @@
#ifndef __MACHINE_H_
#define __MACHINE_H_
#endif

View File

@ -0,0 +1,93 @@
/* $Id: math.h,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
#ifndef _MATH_
#define _MATH_
#ifdef FLOAT
float sin(float x);
float cos(float x);
float tan(float x);
float atan(float x);
float exp(float x);
float log(float x);
float pow(float x);
float sqrt(float x);
#else
double acos(double x);
double acosh(double x);
double asin(double x);
double atan(double x);
double atan2(double y, double x);
double atanh(double x);
double ceil(double x);
double cos(double x);
double cosh(double x);
double exp(double x);
double fabs(double x);
double floor(double x);
double fmod(double x, double y);
double frexp(double x, int *i);
double ldexp(double x, int i);
double log(double x);
double log10(double x);
double modf(double x, double *i);
double pow(double x,double y);
double sin(double x);
double sinh(double x);
double sqrt(double x);
double tan(double x);
double tanh(double x);
#endif
float acosf(float x);
float asinf(float x);
float atan2f(float y, float x);
float atanf(float x);
float ceilf(float x);
float cosf(float x);
float coshf(float x);
float expf(float x);
float fabsf(float x);
float floorf(float x);
float fmodf(float x, float y);
float frexpf(float x, int *i);
float ldexpf(float x, int i);
float log10f(float x);
float logf(float x);
float modff(float x, float *i);
float powf(float x);
float sinf(float x);
float sinhf(float x);
float sqrtf(float x);
float tanf(float x);
float tanhf(float x);
static inline void tgt_fpuenable()
{
#if __mips < 3 || __mips == 32
asm(\
"mfc0 $2,$12;\n" \
"li $3,0x30000000 #ST0_CU1;\n" \
"or $2,$3;\n" \
"mtc0 $2,$12;\n" \
"li $2,0x00000000 #FPU_DEFAULT;\n" \
"ctc1 $2,$31;\n" \
:::"$2","$3"
);
#else
asm(\
"mfc0 $2,$12;\n" \
"li $3,0x34000000 #ST0_CU1;\n" \
"or $2,$3;\n" \
"mtc0 $2,$12;\n" \
"li $2,0x00000000 #FPU_DEFAULT;\n" \
"ctc1 $2,$31;\n" \
:::"$2","$3"
);
#endif
}
#endif /* _MATH_ */

View File

@ -0,0 +1,181 @@
/* $Id: ns16550.h,v 1.1.1.1 2006/09/14 01:59:08 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
/*
* NS16550 UART registers
*/
#ifndef __NS16550_H_
#define __NS16550_H_
#define NS16550_CHANA PHYS_TO_K1(UART0_BASE)
#define NS16550_CHANB PHYS_TO_K1(UART1_BASE)
#if (!defined(__LANGUAGE_ASSEMBLY) && !defined(_LOCORE))
#ifndef nsreg
#ifndef USE_SM502_UART0
#define nsreg(x) unsigned char x
#else
#define nsreg(x) unsigned int x
#endif
#endif
typedef struct {
nsreg(data); /* data register (R/W) */
nsreg(ier); /* interrupt enable (W) */
nsreg(iir); /* interrupt identification (R) */
#define fifo iir /* 16550 fifo control (W) */
nsreg(cfcr); /* line control register (R/W) */
nsreg(mcr); /* modem control register (R/W) */
nsreg(lsr); /* line status register (R/W) */
nsreg(msr); /* modem status register (R/W) */
nsreg(scr); /* scratch register (R/W) */
} ns16550dev;
extern int ns16550 __P((int, struct DevEntry *, unsigned long, int));
#else
/*
* Standard speeds, make these available for start.S et al.
*/
#define B0 0
#define B50 50
#define B75 75
#define B110 110
#define B134 134
#define B150 150
#define B200 200
#define B300 300
#define B600 600
#define B1200 1200
#define B1800 1800
#define B2400 2400
#define B4800 4800
#define B9600 9600
#define B19200 19200
#define B38400 38400
#define B7200 7200
#define B14400 14400
#define B28800 28800
#define B57600 57600
#define B76800 76800
#define B115200 115200
#define B230400 230400
#endif /* __LANGUAGE_ASSEMBLY */
#ifndef NSREG
#define NSREG(x) x
#endif
#define NS16550_DATA 0
#define NS16550_IER 1
#define NS16550_IIR 2
#define NS16550_FIFO 2
#define NS16550_CFCR 3
#define NS16550_MCR 4
#define NS16550_LSR 5
#define NS16550_MSR 6
#define NS16550_SCR 7
/* interrupt enable register */
#define IER_ERXRDY 0x1 /* int on rx ready */
#define IER_ETXRDY 0x2 /* int on tx ready */
#define IER_ERLS 0x4 /* int on line status change */
#define IER_EMSC 0x8 /* int on modem status change */
/* interrupt identification register */
#define IIR_IMASK 0xf /* mask */
#define IIR_RXTOUT 0xc /* receive timeout */
#define IIR_RLS 0x6 /* receive line status */
#define IIR_RXRDY 0x4 /* receive ready */
#define IIR_TXRDY 0x2 /* transmit ready */
#define IIR_NOPEND 0x1 /* nothing */
#define IIR_MLSC 0x0 /* modem status */
#define IIR_FIFO_MASK 0xc0 /* set if FIFOs are enabled */
/* fifo control register */
#define FIFO_ENABLE 0x01 /* enable fifo */
#define FIFO_RCV_RST 0x02 /* reset receive fifo */
#define FIFO_XMT_RST 0x04 /* reset transmit fifo */
#define FIFO_DMA_MODE 0x08 /* enable dma mode */
#define FIFO_TRIGGER_1 0x00 /* trigger at 1 char */
#define FIFO_TRIGGER_4 0x40 /* trigger at 4 chars */
#define FIFO_TRIGGER_8 0x80 /* trigger at 8 chars */
#define FIFO_TRIGGER_14 0xc0 /* trigger at 14 chars */
/* character format control register */
#define CFCR_DLAB 0x80 /* divisor latch */
#define CFCR_SBREAK 0x40 /* send break */
#define CFCR_PZERO 0x30 /* zero parity */
#define CFCR_PONE 0x20 /* one parity */
#define CFCR_PEVEN 0x10 /* even parity */
#define CFCR_PODD 0x00 /* odd parity */
#define CFCR_PENAB 0x08 /* parity enable */
#define CFCR_STOPB 0x04 /* 2 stop bits */
#define CFCR_8BITS 0x03 /* 8 data bits */
#define CFCR_7BITS 0x02 /* 7 data bits */
#define CFCR_6BITS 0x01 /* 6 data bits */
#define CFCR_5BITS 0x00 /* 5 data bits */
/* modem control register */
#define MCR_LOOPBACK 0x10 /* loopback */
#define MCR_IENABLE 0x08 /* output 2 = int enable */
#define MCR_DRS 0x04 /* output 1 = xxx */
#define MCR_RTS 0x02 /* enable RTS */
#define MCR_DTR 0x01 /* enable DTR */
/* line status register */
#define LSR_RCV_FIFO 0x80 /* error in receive fifo */
#define LSR_TSRE 0x40 /* transmitter empty */
#define LSR_TXRDY 0x20 /* transmitter ready */
#define LSR_BI 0x10 /* break detected */
#define LSR_FE 0x08 /* framing error */
#define LSR_PE 0x04 /* parity error */
#define LSR_OE 0x02 /* overrun error */
#define LSR_RXRDY 0x01 /* receiver ready */
#define LSR_RCV_MASK 0x1f
/* modem status register */
#define MSR_DCD 0x80 /* DCD active */
#define MSR_RI 0x40 /* RI active */
#define MSR_DSR 0x20 /* DSR active */
#define MSR_CTS 0x10 /* CTS active */
#define MSR_DDCD 0x08 /* DCD changed */
#define MSR_TERI 0x04 /* RI changed */
#define MSR_DDSR 0x02 /* DSR changed */
#define MSR_DCTS 0x01 /* CTS changed */
#endif

View File

@ -0,0 +1,24 @@
#ifndef STDIO_H
#define STDIO_H
#include <common.h>
int printf (char *fmt, ...);
int sprintf (char *buf, const char *fmt, ...);
struct FILE{
char* str;
size_t pos;
};
typedef struct FILE FILE;
#define EOF 0xFFFFFFFF
FILE* fopen(char* str);
size_t fread(void* ptr, size_t size, size_t nmemb, FILE* stream);
void fclose(FILE* stream);
char *fgets(char *s, int size, FILE *stream);
int sscanf(const char *str, const char *fmt, ...);
int getc(FILE* stream);
#endif

View File

@ -0,0 +1 @@
#define NULL ((void *)0)

View File

@ -0,0 +1,25 @@
#ifndef STRING_H
#define STRING_H
size_t strlen(const char *s);
size_t strnlen(const char *s, size_t len);
char *strcpy(char *dst, const char *src);
char *strncpy(char *dst, const char *src, size_t len);
int strcmp(const char *s1, const char *s2);
int strncmp(const char *s1, const char *s2, size_t n);
char *strchr(const char *s, char c);
char *strfind(const char *s, char c);
//long strtol(const char *s, char **endptr, int base);
void *memset(void *s, char c, size_t n);
void *memmove(void *dst, const void *src, size_t n);
void *memcpy(void *dst, const void *src, size_t n);
int memcmp(const void *v1, const void *v2, size_t n);
void bzero(void *s, size_t n);
#endif

View File

@ -0,0 +1,46 @@
#ifndef _TIME_H_H
#define _TIME_H_H
typedef unsigned long _clock_t;
typedef unsigned long clock_t;
#define MSEC_PER_SEC 1000L
#define USEC_PER_MSEC 1000L
#define NSEC_PER_USEC 1000L
#define NSEC_PER_MSEC 1000000L
#define USEC_PER_SEC 1000000L
#define NSEC_PER_SEC 1000000000L
#define FSEC_PER_SEC 1000000000000000LL
struct tms{
_clock_t tms_utime;
_clock_t tms_stime;
_clock_t tms_cutime;
_clock_t tms_cstime;
};
struct tm{
int tm_sec;
int tm_min;
int tm_hour;
int tm_mday;
int tm_mon;
int tm_year;
int tm_wday;
int tm_yday;
};
struct timespec{
_clock_t tv_sec;
_clock_t tv_nsec;
_clock_t tv_usec;
_clock_t tv_msec;
};
struct timeval{
_clock_t tv_sec;
_clock_t tv_nsec;
_clock_t tv_usec;
_clock_t tv_msec;
};
unsigned long get_count();
#endif

View File

@ -0,0 +1,21 @@
CFLAGS := -D_KERNEL -DCONFIG_PAGE_SIZE_16KB -fno-builtin -mips1 -DCACHELOCK_MEM
CFLAGS += -DCPU_COUNT_PER_US=100 -I include -include common.h -DAPB_CLK=33333333
CFLAGS += -DLS1FSOC -DCPU_MULT=6 -DDDR_MULT=6 -msoft-float -EL
CFLAGS += $(MEM_DEF)
.SUFFIXES: .o64 .elf64 .bin64
objs= malloc.o stdio.o printf.o udelay.o now.o putchar.o puts.o printhex.o printbase.o memcmp.o strcat.o strchr.o strcmp.o strtok.o strspn.o strcspn.o getchar.o testchar.o vsprintf.o atob.o sprintf.o strtoupp.o toupper.o string.o str_fmt.o strcpy.o strichr.o strncmp.o strncpy.o newprintf.o cache.o cmdline.o irq.o guess.o strtoul.o time.o exception.o sscanf.o
objs64=$(objs:.o=.o64)
libtinyc.a: $(objs)
$(CROSS_COMPILE)ar -cr $@ $^
libtinyc64.a: $(objs64)
$(CROSS_COMPILE)ar -cr $@ $^
clean:
rm -f *.o *.a *.s *.o64 *.bin64 *.elf64
-include rules.make

View File

@ -0,0 +1,224 @@
static char * _getbase __P((char *, int *));
#ifdef HAVE_QUAD
static int _atob __P((unsigned long long *, char *p, int));
#else
static int _atob __P((unsigned long *, char *, int));
#endif
static char *
_getbase(char *p, int *basep)
{
if (p[0] == '0') {
switch (p[1]) {
case 'x':
*basep = 16;
break;
case 't': case 'n':
*basep = 10;
break;
case 'o':
*basep = 8;
break;
default:
*basep = 10;
return (p);
}
return (p + 2);
}
*basep = 10;
return (p);
}
/*
* _atob(vp,p,base)
*/
static int
#ifdef HAVE_QUAD
_atob (u_quad_t *vp, char *p, int base)
{
u_quad_t value, v1, v2;
#else
_atob (unsigned long *vp, char *p, int base)
{
u_long value, v1, v2;
#endif
char *q, tmp[20];
int digit;
if (p[0] == '0' && (p[1] == 'x' || p[1] == 'X')) {
base = 16;
p += 2;
}
if (base == 16 && (q = strchr (p, '.')) != 0) {
if (q - p > sizeof(tmp) - 1)
return (0);
strncpy (tmp, p, q - p);
tmp[q - p] = '\0';
if (!_atob (&v1, tmp, 16))
return (0);
q++;
if (strchr (q, '.'))
return (0);
if (!_atob (&v2, q, 16))
return (0);
*vp = (v1 << 16) + v2;
return (1);
}
value = *vp = 0;
for (; *p; p++) {
if (*p >= '0' && *p <= '9')
digit = *p - '0';
else if (*p >= 'a' && *p <= 'f')
digit = *p - 'a' + 10;
else if (*p >= 'A' && *p <= 'F')
digit = *p - 'A' + 10;
else
return (0);
if (digit >= base)
return (0);
value *= base;
value += digit;
}
*vp = value;
return (1);
}
/*
* atob(vp,p,base)
* converts p to binary result in vp, rtn 1 on success
*/
int
atob(uint32_t *vp, char *p, int base)
{
#ifdef HAVE_QUAD
u_quad_t v;
#else
u_long v;
#endif
if (base == 0)
p = _getbase (p, &base);
if (_atob (&v, p, base)) {
*vp = v;
return (1);
}
return (0);
}
#ifdef HAVE_QUAD
/*
* llatob(vp,p,base)
* converts p to binary result in vp, rtn 1 on success
*/
int
llatob(u_quad_t *vp, char *p, int base)
{
if (base == 0)
p = _getbase (p, &base);
return _atob(vp, p, base);
}
#endif
/*
* char *btoa(dst,value,base)
* converts value to ascii, result in dst
*/
char *
btoa(char *dst, u_int value, int base)
{
char buf[34], digit;
int i, j, rem, neg;
if (value == 0) {
dst[0] = '0';
dst[1] = 0;
return (dst);
}
neg = 0;
if (base == -10) {
base = 10;
if (value & (1L << 31)) {
value = (~value) + 1;
neg = 1;
}
}
for (i = 0; value != 0; i++) {
rem = value % base;
value /= base;
if (rem >= 0 && rem <= 9)
digit = rem + '0';
else if (rem >= 10 && rem <= 36)
digit = (rem - 10) + 'a';
buf[i] = digit;
}
buf[i] = 0;
if (neg)
strcat (buf, "-");
/* reverse the string */
for (i = 0, j = strlen (buf) - 1; j >= 0; i++, j--)
dst[i] = buf[j];
dst[i] = 0;
return (dst);
}
#ifdef HAVE_QUAD
/*
* char *btoa(dst,value,base)
* converts value to ascii, result in dst
*/
char *
llbtoa(char *dst, u_quad_t value, int base)
{
char buf[66], digit;
int i, j, rem, neg;
if (value == 0) {
dst[0] = '0';
dst[1] = 0;
return (dst);
}
neg = 0;
if (base == -10) {
base = 10;
if (value & (1LL << 63)) {
value = (~value) + 1;
neg = 1;
}
}
for (i = 0; value != 0; i++) {
rem = value % base;
value /= base;
if (rem >= 0 && rem <= 9)
digit = rem + '0';
else if (rem >= 10 && rem <= 36)
digit = (rem - 10) + 'a';
buf[i] = digit;
}
buf[i] = 0;
if (neg)
strcat (buf, "-");
/* reverse the string */
for (i = 0, j = strlen (buf) - 1; j >= 0; i++, j--)
dst[i] = buf[j];
dst[i] = 0;
return (dst);
}
#endif

View File

@ -0,0 +1,49 @@
#include <asm/r4kcache.h>
int dcache_size = 0x4000;
int icache_size = 0x4000;
#define cpu_dcache_line_size() 32
void dma_cache_wback_inv(unsigned long addr, unsigned long size)
{
/*
* Either no secondary cache or the available caches don't have the
* subset property so we have to flush the primary caches
* explicitly
*/
if (size >= dcache_size) {
blast_dcache32();
} else {
blast_dcache_range(addr, addr + size);
}
}
void dma_cache_inv(unsigned long addr, unsigned long size)
{
if (size >= dcache_size) {
blast_dcache32();
} else {
unsigned long lsize = cpu_dcache_line_size();
unsigned long almask = ~(lsize - 1);
cache_op(Hit_Writeback_Inv_D, addr & almask);
cache_op(Hit_Writeback_Inv_D, (addr + size - 1) & almask);
blast_inv_dcache_range(addr, addr + size);
}
}
void flush_icache_range(unsigned long start, unsigned long end)
{
if (end - start >= dcache_size) {
blast_dcache32();
} else {
protected_blast_dcache_range(start, end);
}
if (end - start > icache_size)
blast_icache32();
else
protected_blast_icache_range(start, end);
}

View File

@ -0,0 +1,186 @@
/*
* cmdline.c
* Use command to do testing, use "help" to get more information.
*
* Created on: 2013-1-10
* Author: liming
*/
#include <cmdline.h>
int do_exit();
int do_nothing();
int do_help(int argc, void *argv[]);
int do_d4(int argc, char **argv);
int testguess(int argc, char **argv);
const cmdline_t cmd[] = {
{"exit", do_exit, 0, "[exit]", "--logout"},
{"help", do_help, 1, "[help <command>]", "--cmd list"},
{"guess", testguess, 6,"","guess from to mask stide mode"},
{"d4", do_d4, 2,"","d4 addr [count]"},
{0, do_nothing, 0, "", ""}
}; //命令名按字母表的顺序
int do_d4(int argc, char **argv)
{
unsigned int addr;
int i, num;
if(argc < 2)
{
printf("\nusage: d4 <addr> <num>");
return 1;
}
addr = strtoul(argv[1],0,0);
if(argc == 2) num = 1;
else num = strtoul(argv[2],0,0);
for(i=0; i<num; i++)
{
if((i%4) == 0)
printf("\n0x%08x:\t", addr+i*4);
printf(" %08x ", *(volatile unsigned int*)(addr+i*4));
}
return 0;
}
int do_exit()
{
return 0;
}
int do_nothing()
{
return 0;
}
int do_help(int argc, void *argv[])
{
int i;
char *s;
if(argc<2)
{
printf("\ncommands:\n\n");
for(i=0; cmd[i].cmdname; i++)
{
printf("\t%s\t%s\t%s\n", cmd[i].cmdname, cmd[i].usage, cmd[i].expression);
}
}
else
{
s = (char *)argv[1];
for(i=0; cmd[i].cmdname; i++)
{
if(strcmp(s, cmd[i].cmdname)==0)
{
printf("\n\t%s\t%s\t%s\n", cmd[i].cmdname, cmd[i].usage, cmd[i].expression);
break;
}
}
if(!(cmd[i].cmdname))
{
printf("\n\tERROR: undefine command!!!\n");
}
}
return 0;
}
/*The format of cmd is "$xxx xx xx xx". */
int cmdloop(void)
{
char c;
char cmdbuffer[CMD_BUFF]={0};
//int (*op)(int argc, char **argv);
int (*op)(int argc, void *argv[]);
int argc;
char *argv[V_NUM]={0};
char *cmdptr;
short cp, i, j, k;
int history = 11; //指向help命令
int history_num = 0;
char hispara[V_NUM][V_LEN];
char *history_para[V_NUM];
while(1)
{
printf("\n$ ");
cp = 0; //current position
while(1) // internal loop
{
c = getchar();
if((c>0x1f)&&(c<0x7f)) //no ctrl_char
{
cmdbuffer[cp++] = c;
putchar(c);
}
else if((c == 0x8 || c == 0x7f) && cp) //backspace
{
cp--;
cmdbuffer[cp] = '\0';
putchar(0x8);
putchar(0x20); //This is an interesting way.
putchar(0x8);
}
else if((c==0xa) || (c==0xd))
{
break;
}
}
if(cp == 0)
{
if(!argv[0])
continue;
}
else
{
char *p0;
char c0, c;
for(i=0, argc=0, p0=cmdbuffer, c0=0; i<cp; i++)
{
if((c = cmdbuffer[i]) == 0x20) //space
{
cmdbuffer[i] = 0;
}
else if(c0==0x20)
{
argv[argc++] = p0;
p0 = cmdbuffer+i;
}
c0 = c;
}
if(c0!=0x20) argv[argc++] = p0;
cmdbuffer[i] = 0;
}
if(strcmp(argv[0], cmd[0].cmdname)==0) break; //exit
else
{
for(k=1; cmd[k].cmdname; k++)
{
if(strcmp(argv[0], cmd[k].cmdname)==0)
{
op = cmd[k].func;
op(argc, argv);
if(cmd[k].repeat)
{
history = k; //current cmd
history_num = argc;
}
else argv[0] = 0;
break;
}
}
if(!(cmd[k].cmdname))
{
printf("\n\tERROR: undefine command!!!\n");
}
}
}
return 0;
}

View File

@ -0,0 +1,30 @@
unsigned long get_epc(void)
{
unsigned long n;
asm(
"mfc0 %0,$14\n\t"
:"=r"(n)
);
return n;
}
unsigned long get_cause(void)
{
unsigned long n;
asm(
"mfc0 %0,$13\n\t"
:"=r"(n)
);
return n;
}
void exception(void)
{
unsigned long n;
printf("There is an exception!!\n");
n=get_epc();
printf("The epc is %x\n",n);
n=get_cause();
printf("The cause is %x\n",n);
return;
}

View File

@ -0,0 +1,4 @@
int getchar()
{
return tgt_getchar();
}

View File

@ -0,0 +1,122 @@
#ifdef _ABIO32
#define LADDU "addu"
#else
#define LADDU "daddu"
#endif
static unsigned long GUESS_ADDR = ((int)0xbfc00000);
static unsigned long mask = 0xffff;
static unsigned long stride = 4;
int scan()
{
void *p;
for(p=0xffffffff90000000;p<0xffffffffa0000000;p=p+4)
{
if((((long)p)&0xffff)==0) printf("%x\n", p);
*(volatile int *)p;
}
}
int guess(unsigned long addr, unsigned long end)
{
while(addr<end)
{
printf("g%x\n", addr);
asm volatile(
".set push;\n"
".set noreorder;\n"
".set mips64;\n"
"1:lw %1,(%2);\n"
"beqzl %1,1f;\n"
"nop;\n"
"sync;\n"
LADDU " %0, %5;\n"
"and %1, %0, %4;\n"
"beqz %1,2f;\n"
"nop;\n"
"b 1b;\n"
"nop;\n"
"1:lw %1,(%0);\n"
"b 1b;\n"
"nop;\n"
"2:\n"
".set pop;\n"
:"=r"(addr):"r"(0),"r"(GUESS_ADDR),"0"(addr),"r"(mask), "r"(stride)
);
}
}
int guess1(unsigned long addr, unsigned long end)
{
while(addr<end)
{
printf("G%x\n", addr);
asm volatile(
".set push;\n"
".set noreorder;\n"
".set mips64;\n"
"1:lw %1,(%2);\n"
"beqzl %1,1f;\n"
"nop;\n"
"sync;\n"
LADDU " %0,%5;\n"
"and %1, %0, %4;\n"
"beqz %1,2f;\n"
"nop;\n"
"b 1b;\n"
"nop;\n"
"1:jr %0;\n"
"nop;\n"
"2:\n"
".set pop;\n"
:"=r"(addr):"r"(0),"r"(GUESS_ADDR),"0"(addr),"r"(mask),"r"(stride)
);
}
}
int testguess(int argc, char **argv)
{
long from, to, mode;
from = 0xbf000000;
to = 0xc0000000;
mode = 3;
while(*(volatile int *)GUESS_ADDR == 0)
GUESS_ADDR += 4;
printf("guess addr %x\n",GUESS_ADDR);
printf("begin test\n");
// scan();
if(argc>1) from = strtoul(argv[1],0,0);
if(argc>2) to = strtoul(argv[2],0,0);
if(argc>3) mask = strtoul(argv[3],0,0);
if(argc>4) stride = strtoul(argv[4],0,0);
if(argc>5) mode = strtoul(argv[5],0,0);
if(argc>2)
{
if(mode&1)
guess1(from, to);
if(mode&2)
guess(from, to);
}
else
{
if(mode&1)
guess1(0xffffffffbf000000, 0xffffffffc0000000);
if(mode&2)
guess(0xffffffffbf000000, 0xffffffffc0000000);
if(mode&1)
guess1(0xffffffff9f000000, 0xffffffffa0000000);
if(mode&2)
guess(0xffffffff9f000000, 0xffffffffa0000000);
}
return 0;
}

414
resources/project/lib/irq.c Normal file
View File

@ -0,0 +1,414 @@
#include <asm/mipsregs.h>
#include <errno.h>
#include <irq.h>
#include <stdlib.h>
static int no_action(int cpl, void *dev_id)
{
return 0;
}
static struct irqaction cascade_irqaction = {
.handler = no_action,
.name = "cascade",
};
unsigned int ack_sb2f_board_irq(unsigned int irq_nr)
{
//printf("ack_sb2f_board_irq %d\n",irq_nr);
(sb2f_board_hw0_icregs+(irq_nr>>5))->int_clr |= (1 << (irq_nr & 0x1f));
}
unsigned int disable_sb2f_board_irq(unsigned int irq_nr)
{
//printf("disable_sb2f_board_irq %d\n",irq_nr);
(sb2f_board_hw0_icregs+(irq_nr>>5))->int_en &= ~(1 << (irq_nr & 0x1f));
}
unsigned int enable_sb2f_board_irq(unsigned int irq_nr)
{
//printf("enable_sb2f_board_irq %d\n",irq_nr);
(sb2f_board_hw0_icregs+(irq_nr>>5))->int_en |= (1 << (irq_nr & 0x1f));
}
int sb2f_board_irq_set_type(unsigned int irq,unsigned int flow_type)
{
unsigned int irq_nr = irq;
int mode;
}
struct irq_chip sb2f_board_irq_chip = {
.name = "SB2F BOARD",
.ack = ack_sb2f_board_irq,
.mask = disable_sb2f_board_irq,
.unmask = enable_sb2f_board_irq,
.eoi = enable_sb2f_board_irq,
.set_type = sb2f_board_irq_set_type
};
struct irq_desc irq_desc[256];
int handle_IRQ_event(unsigned int irq,struct irqaction *action)
{
// printf("I am in handle_IRQ_EVENT\n");
#ifdef MYOPROFILE
local_irq_enable();
#endif
do {
action->handler(action->dev_id);
action = action->next;
}while (action);
#ifdef MYOPROFILE
local_irq_disable();
#endif
// printf("I am out handle_IRQ_EVENT\n");
}
void handle_level_irq(unsigned int irq,struct irq_desc *desc)
{
// printf("i am in handle_level_irq\n");
struct irqaction *action;
desc->chip->mask(irq);/*可以清楚原因寄存器*/
desc->chip->ack(irq);/*可以清除中断状态寄存器*/
action = desc->action;
handle_IRQ_event(irq,action);
desc->chip->unmask(irq);
// printf("i am out handle_level_irq\n");
}
void generic_handle_irq(unsigned int irq)
{
// printf("i am in generic_handler_irq\n");
// CP0_Cause();
struct irq_desc *desc = irq_desc + irq;
desc->handle_irq(irq,desc);
// printf("i am out generic_handler_irq\n");
}
#define do_IRQ(irq) do{ generic_handle_irq(irq);}while(0)
void ls1gp_board_dma_irqdispatch();
void ls1b_board_hw_irqdispatch(int n)
{
int irq;
int intstatus;
intstatus = (sb2f_board_hw0_icregs + n)->int_isr;
irq = ffs(intstatus);
if(!irq)
{
printf("Unknow interrpt intstatus %x\n",intstatus);
}
else if(n == 1 && irq == 11)
{
ls1gp_board_dma_irqdispatch();
}
else do_IRQ(n*32+irq-1);
}
void __set_irq_handler(unsigned int irq, irq_flow_handler_t handler, int is_chained, const char *name)
{
struct irq_desc *desc;
desc = irq_desc + irq;
desc->handle_irq = handler;
}
void default_enable(unsigned int irq)
{
struct irq_desc *desc = irq_desc + irq;
desc->chip->unmask(irq);
}
void default_disable(unsigned int irq)
{
}
unsigned int default_startup(unsigned int irq)
{
irq_desc[irq].chip->enable(irq);
return 0;
}
void irq_chip_set_defaults(struct irq_chip *chip)
{
if(!chip->enable)
chip->enable = default_enable;
if(!chip->disable)
chip->disable = default_disable;
if(!chip->startup)
chip->startup = default_startup;
if(!chip->shutdown)
chip->shutdown = chip->disable;
}
int set_irq_chip(unsigned int irq,struct irq_chip *chip)
{
struct irq_desc *desc;
desc = irq_desc + irq;
irq_chip_set_defaults(chip);
desc->chip = chip;
return 0;
}
void set_irq_chip_and_handler(unsigned int irq,struct irq_chip *chip,irq_flow_handler_t handle)
{
set_irq_chip(irq,chip);
__set_irq_handler(irq, handle, 0, NULL);
}
/*setup dma irq */
struct ls1gp_cop_global_regs
{
volatile unsigned int control;
volatile unsigned int rd_inten;
volatile unsigned int wr_inten;
volatile unsigned int rd_intisr; /* offset 0x10*/
volatile unsigned int wr_intisr;
unsigned int unused[11];
} ;
#define LS1GP_BOARD_DMA_IRQ_BASE 168
#define LS1GP_BOARD_DMA_IRQ_COUNT 16
static struct ls1gp_cop_global_regs *ls1gp_cop_global_regs = (void *)0xbc000000;
void ls1gp_board_dma_irqdispatch()
{
int intstatus;
int irq;
intstatus = (ls1gp_cop_global_regs->wr_intisr & 0xff) << 8 | (ls1gp_cop_global_regs->rd_intisr & 0xff);
irq=ffs(intstatus);
if(!irq){
printf("Unknow dma interrupt status %x \n" , intstatus);
return;
}
else do_IRQ(LS1GP_BOARD_DMA_IRQ_BASE + irq - 1);
}
void disable_ls1gp_dma_irq(unsigned int irq)
{
int irq_nr;
if(irq < LS1GP_BOARD_DMA_IRQ_BASE + 8)
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE;
ls1gp_cop_global_regs->rd_inten &= ~(1<<irq_nr);
}
else
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE - 8;
ls1gp_cop_global_regs->wr_inten &= ~(1<<irq_nr);
}
}
void enable_ls1gp_dma_irq(unsigned int irq)
{
int irq_nr;
if(irq < LS1GP_BOARD_DMA_IRQ_BASE + 8)
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE;
printf("rd irq_nr %d\n",irq_nr);
ls1gp_cop_global_regs->rd_inten |= (1<<irq_nr);
}
else
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE - 8;
ls1gp_cop_global_regs->wr_inten |= (1<<irq_nr);
}
}
static void ack_ls1gp_dma_irq(unsigned int irq)
{
int irq_nr;
if(irq < LS1GP_BOARD_DMA_IRQ_BASE + 8)
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE;
ls1gp_cop_global_regs->rd_intisr = (1<<irq_nr);
}
else
{
irq_nr =irq - LS1GP_BOARD_DMA_IRQ_BASE - 8;
ls1gp_cop_global_regs->wr_intisr = (1<<irq_nr);
}
}
static void end_ls1gp_dma_irq(unsigned int irq)
{
enable_ls1gp_dma_irq(irq);
}
static struct irq_chip ls1gp_dma_irq_chip = {
.name = "LS1GP BOARD",
.ack = ack_ls1gp_dma_irq,
.mask = disable_ls1gp_dma_irq,
.unmask = enable_ls1gp_dma_irq,
.eoi = enable_ls1gp_dma_irq,
.end = end_ls1gp_dma_irq,
};
void ls1gp_dma_irq_init()
{
int irq;
for (irq = LS1GP_BOARD_DMA_IRQ_BASE; irq < LS1GP_BOARD_DMA_IRQ_BASE + LS1GP_BOARD_DMA_IRQ_COUNT; irq++) {
set_irq_chip_and_handler(irq, &ls1gp_dma_irq_chip, handle_level_irq);
}
}
void sb2f_board_irq_init()
{
int i;
for(i = 0;i <= 159;i++)
{
set_irq_chip_and_handler(i,&sb2f_board_irq_chip,handle_level_irq);
}
}
int setup_irq(unsigned int irq, struct irqaction *newaction)
{
struct irq_desc *desc = irq_desc + irq;
struct irqaction *old, **p;
int shared = 0;
p = &desc->action;
old = *p;
if(old)
{
do
{
p = &old->next;
old= *p;
}while(old);
shared = 1;
}
*p = newaction;
if(!shared)
{
irq_chip_set_defaults(desc->chip);
if(newaction->flags & IRQF_TRIGGER_MASK)
if(desc->chip && desc->chip->set_type)
desc->chip->set_type(irq,newaction->flags & IRQF_TRIGGER_MASK);
if(desc->chip->startup)
desc->chip->startup(irq);
else
desc->chip->enable(irq);
}
return 0;
}
int request_irq(unsigned int irq, irq_handler_t handler, unsigned long irqflags,const char *devname, void *dev_id)
{
struct irqaction *action;
int retval;
if(!handler)
return -EINVAL;
action = malloc(sizeof(struct irqaction));
if(!action)
return -ENOMEM;
action->handler = handler;
action->flags = irqflags;
action->next = NULL;
action->name = devname;
action->dev_id = dev_id;
action->irq = irq;
setup_irq(irq,action);
}
///////interrupt
#define INT_PCI_INTA (1<<6)
#define INT_PCI_INTB (1<<7)
#define INT_PCI_INTC (1<<8)
#define INT_PCI_INTD (1<<9)
#define ST0_IM 0x0000ff00
#define CAUSEF_IP7 ( 1 << 15)
#define CAUSEF_IP6 ( 1 << 14)
#define CAUSEF_IP5 ( 1 << 13)
#define CAUSEF_IP4 ( 1 << 12)
#define CAUSEF_IP3 ( 1 << 11)
#define CAUSEF_IP2 ( 1 << 10)
extern struct sb2f_board_intc_regs volatile *sb2f_board_hw0_icregs;
void plat_irq_dispatch(struct pt_regs *regs)
{
unsigned int cause = read_c0_cause() & ST0_IM;
unsigned int status = read_c0_status() & ST0_IM;
unsigned int pending = cause & status;
if(pending & CAUSEF_IP7)
{
#ifdef MYOPROFILE
unsigned long epc;
extern char _ftext[];
extern int irqdepth;
/*only sample in irq*/
#if 1
if(irqdepth>1)
#endif
{
epc = read_c0_epc();
if(epc>=0x80000000) (*(unsigned int *)(epc-(unsigned long)_ftext+0x84000000))++;
}
write_c0_compare(read_c0_count()+MYOPROFILE_TICK);
#else
static int cnt=0;
printf("cnt %d\n",cnt++);
write_c0_compare(read_c0_count()+100000000/100);
#endif
}
else if(pending & CAUSEF_IP2)
{
ls1b_board_hw_irqdispatch(0);
}
else if(pending & CAUSEF_IP3)
{
ls1b_board_hw_irqdispatch(1);
}
else if(pending & CAUSEF_IP4)
{
ls1b_board_hw_irqdispatch(2);
}
else if(pending & CAUSEF_IP5)
{
ls1b_board_hw_irqdispatch(3);
}
else if(pending & CAUSEF_IP6)
{
ls1b_board_hw_irqdispatch(4);
}
else
{
printf("spurious interrupt\n");
}
}
void init_IRQ()
{
int i;
#ifdef MYOPROFILE
memset((void *)0x84000000, 0, 0x200000);
#endif
for(i = 0;i < 5;i++)
{
/* active level setting */
/* uart, keyboard, and mouse are active high */
(sb2f_board_hw0_icregs+i)->int_pol = -1; /*active high*/
/* make all interrupts level triggered */
(sb2f_board_hw0_icregs+i)->int_edge = 0x00000000;
/* mask all interrupts */
(sb2f_board_hw0_icregs+i)->int_clr = 0xffffffff;
}
sb2f_board_irq_init();
ls1gp_dma_irq_init();
setup_irq(32+10, &cascade_irqaction);
clear_c0_status(ST0_IM);
#ifdef MYOPROFILE
write_c0_compare(MYOPROFILE_TICK);
write_c0_count(0);
set_c0_status(0xff01);
#else
set_c0_status(0x7f01);
#endif
}

View File

@ -0,0 +1,135 @@
/* $Id: malloc.c,v 1.1.1.1 2006/09/14 01:59:08 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
typedef long long ALIGN;
//static void free(void *ap);
union header {
struct {
union header *ptr;
unsigned size;
} s;
ALIGN x;
};
typedef union header HEADER;
static HEADER base;
static HEADER *allocp; /* K&R called allocp, freep */
#ifndef NULL
#define NULL 0
#endif
#define NALLOC 128
/* The rest of this file is from pages 185-189 of K & R Edition 2 */
static HEADER *morecore (unsigned nbyte);
char *membase=0x80010000;
char *sbrk(int size)
{
char *p=membase;
membase +=size;
return p;
}
void *
malloc(size_t nbytes)
{
HEADER *p, *q; /* K&R called q, prevp */
unsigned nunits;
nunits = (nbytes + sizeof (HEADER) - 1) / sizeof (HEADER) + 1;
if ((q = allocp) == NULL) { /* no free list yet */
base.s.ptr = allocp = q = &base;
base.s.size = 0;
}
for (p = q->s.ptr;; q = p, p = p->s.ptr) {
if (p->s.size >= nunits) { /* big enough */
if (p->s.size == nunits) /* exactly */
q->s.ptr = p->s.ptr;
else { /* allocate tail end */
p->s.size -= nunits;
p += p->s.size;
p->s.size = nunits;
}
allocp = q;
return ((char *)(p + 1));
}
if (p == allocp)
if ((p = morecore (nunits)) == NULL)
return (NULL);
}
}
static HEADER *
morecore(unsigned nu)
{
char *cp;
HEADER *up;
int rnu;
rnu = NALLOC * ((nu + NALLOC - 1) / NALLOC);
cp = sbrk(rnu * sizeof (HEADER));
if ((int)cp == NULL)
return (NULL);
up = (HEADER *) cp;
up->s.size = rnu;
free ((char *)(up + 1));
return (allocp);
}
void
free(void *ap)
{
HEADER *p, *q;
p = (HEADER *) ap - 1;
for (q = allocp; !(p > q && p < q->s.ptr); q = q->s.ptr)
if (q >= q->s.ptr && (p > q || p < q->s.ptr))
break;
if (p + p->s.size == q->s.ptr) {
p->s.size += q->s.ptr->s.size;
p->s.ptr = q->s.ptr->s.ptr;
} else
p->s.ptr = q->s.ptr;
if (q + q->s.size == p) {
q->s.size += p->s.size;
q->s.ptr = p->s.ptr;
} else
q->s.ptr = p;
allocp = q;
}

View File

@ -0,0 +1,16 @@
/**
* memcmp - Compare two areas of memory
* @cs: One area of memory
* @ct: Another area of memory
* @count: The size of the area.
*/
int memcmp(const void * cs,const void * ct,int count)
{
const unsigned char *su1, *su2;
signed char res = 0;
for( su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)
if ((res = *su1 - *su2) != 0)
break;
return res;
}

View File

@ -0,0 +1,15 @@
void *memcpy(void *s1, const void *s2, size_t n)
{
const char *f = s2;
char *t = s1;
if (f < t) {
f += n;
t += n;
while (n-- > 0)
*--t = *--f;
} else
while (n-- > 0)
*t++ = *f++;
return s1;
}

View File

@ -0,0 +1,9 @@
void * memset(void * s,int c, size_t count)
{
char *xs = (char *) s;
while (count--)
*xs++ = c;
return s;
}

View File

@ -0,0 +1,13 @@
int
newprintf (const char *fmt, ...)
{
int len;
va_list ap;
char buf[1024];
va_start(ap, fmt);
len = vsprintf (buf, fmt, ap);
va_end(ap);
putstring(buf);
return (len);
}

View File

@ -0,0 +1,6 @@
int now()
{
int count;
asm volatile("mfc0 %0,$9":"=r"(count));
return count;
}

View File

@ -0,0 +1,28 @@
int printbase(long v,int w,int base,int sign)
{
int i,j;
int c;
char buf[64];
unsigned long value;
if(sign && v<0)
{
value = -v;
putchar('-');
}
else value=v;
for(i=0;value;i++)
{
buf[i]=value%base;
value=value/base;
}
#define max(a,b) (((a)>(b))?(a):(b))
for(j=max(w,i);j>0;j--)
{
c=j>i?0:buf[j-1];
putchar((c<=9)?c+'0':c-0xa+'a');
}
return 0;
}

View File

@ -0,0 +1,84 @@
int printf(const char *fmt,...)
{
int i;
char c;
void **arg;
void *ap;
int w;
__builtin_va_start(ap,fmt);
arg=ap;
for(i=0;fmt[i];i++)
{
c=fmt[i];
if(c=='%')
{
w=1;
again:
switch(fmt[i+1])
{
case 's':
putstring(*arg);
arg++;
i++;
break;
case 'c':
putchar((long)*arg);
arg++;
i++;
break;
case 'u':
printbase((long)*arg,w,10,0);
arg++;
i++;
break;
case 'd':
printbase((long)*arg,w,10,1);
arg++;
i++;
break;
case 'l':
printbase((long)*arg,w,10,0);
arg++;
i=i+2;
break;
case 'o':
printbase((long)*arg,w,8,0);
arg++;
i++;
break;
case 'b':
printbase((long)*arg,w,2,0);
arg++;
i++;
break;
case 'p':
case 'x':
printbase((long)*arg,w,16,0);
arg++;
i++;
break;
case '%':
putchar('%');
i++;
break;
case '0':
i++;
case '1' ... '9':
for(w=0;fmt[i+1]>'0' && fmt[i+1]<='9';i++)
w=w*10+(fmt[i+1]-'0');
goto again;
break;
default:
putchar('%');
break;
}
}
else{
if(c=='\n') putchar('\r');
putchar(c);
}
}
return 0;
}

View File

@ -0,0 +1,11 @@
int printhex(long v,int w)
{
int i;
int c;
for(i=4*(w-1);i>=0;i-=4)
{
c=(v>>i)&0xf;
putchar((c<=9)?c+'0':c-0xa+'a');
}
return 0;
}

View File

@ -0,0 +1,18 @@
int putchar(int c)
{
tgt_putchar(c);
return 0;
}
void tgt_putchar(c)
{
asm(
".set noreorder\n\t"
"lui $25, 0xbfb0\n\t"
"jr $31\n\t"
"sb %0,-0x10($25)\n\t"
".set reorder\n\t"
:
:"r"(c)
:"$25");
}

View File

@ -0,0 +1,20 @@
int putstring(char *s)
{
char c;
while((c=*s))
{
if(c == '\n') putchar('\r');
putchar(c);
s++;
}
return 0;
}
int puts(char *s)
{
putstring(s);
putchar('\r');
putchar('\n');
return 0;
}

View File

@ -0,0 +1,16 @@
.S.o:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -c $< -nostdinc -nostdlib
.c.o:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -c $< -nostdinc -nostdlib
.S.o64:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -o $@ -c $< -nostdinc -nostdlib -mabi=64
.c.o64:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -o $@ -c $< -nostdinc -nostdlib -mabi=64
.S.s:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -S -fverbose-asm -o $@ $< -nostdinc -nostdlib
.c.s:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -S -fverbose-asm -o $@ $< -nostdinc -nostdlib
.S.s64:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -S -fverbose-asm -o $@ -c $< -nostdinc -nostdlib -mabi=64
.c.s64:
${CROSS_COMPILE}gcc -O2 $(CFLAGS) -fno-pic -mno-abicalls -g -DGUEST -I ../include -I . -S -fverbose-asm -o $@ -c $< -nostdinc -nostdlib -mabi=64

View File

@ -0,0 +1,25 @@
/*
* sprintf(buf,fmt,va_alist) send formatted string to buf
*/
int
sprintf (char *buf, const char *fmt, ...)
{
int n;
va_list ap;
va_start(ap, fmt);
n = vsprintf (buf, fmt, ap);
va_end(ap);
return (n);
}
int
snprintf (char *buf, size_t maxlen, const char *fmt, ...)
{
int n;
va_list ap;
va_start(ap, fmt);
n = vsprintf (buf, fmt, ap);
va_end(ap);
return (n);
}

View File

@ -0,0 +1,512 @@
/*
* The MIT License (MIT)
*
* Copyright (c) 2015 G. Elian Gidoni
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include <stdio.h>
#include <common.h>
/*
* Private functions.
*/
static int
is_space(char c)
{
return (c == ' ' || c == '\t' || c == '\v' ||
c == '\f' || c == '\r' || c == '\n');
}
static char*
skip_spaces(const char *str)
{
while (is_space(*str)){
++str;
}
return (char*)str;
}
/* Returns a pointer after the last read char, or 'str' on error. */
static char*
dec_to_signed(const char *str, long *out)
{
const char * cur = skip_spaces(str);
long value = 0;
int isneg = 0, isempty = 1;
if (cur[0] == '+'){
cur += 1;
}else if(cur[0] == '-'){
cur += 1;
isneg = 1;
}
while (*cur != '\0' && *cur >= '0' && *cur <= '9'){
value = (value * 10) + (*cur - '0');
isempty = 0;
++cur;
}
if (isempty){
return (char*)str;
}
if (isneg){
*out = -value;
}else{
*out = value;
}
return (char*)cur;
}
/* Returns a pointer after the last read char, or 'str' on error. */
static char*
dec_to_unsigned(const char *str, unsigned long *out)
{
const char * cur = skip_spaces(str);
unsigned long value = 0;
int isempty = 1;
while (*cur != '\0' && *cur >= '0' && *cur <= '9'){
value = (value * 10) + (*cur - '0');
isempty = 0;
++cur;
}
if (isempty){
return (char*)str;
}
*out = value;
return (char*)cur;
}
/* Returns a pointer after the last read char, or 'str' on error. */
static char*
hex_to_signed(const char *str, long *out)
{
const char * cur = skip_spaces(str);
long value = 0;
int isneg = 0, isempty = 1;
if (cur[0] == '+'){
cur += 1;
}else if(cur[0] == '-'){
cur += 1;
isneg = 1;
}
if (cur[0] == '0' && cur[1] == 'x'){
cur += 2;
}
while (*cur != '\0'){
if(*cur >= '0' && *cur <= '9'){
value = (value * 16) + (*cur - '0');
}else if (*cur >= 'a' && *cur <= 'f'){
value = (value * 16) + 10 + (*cur - 'a');
}else if (*cur >= 'A' && *cur <= 'F'){
value = (value * 16) + 10 + (*cur - 'A');
}else{
break;
}
isempty = 0;
++cur;
}
if (isempty){
return (char*)str;
}
if (isneg){
*out = -value;
}else{
*out = value;
}
return (char*)cur;
}
/* Returns a pointer after the last read char, or 'str' on error. */
static char*
hex_to_unsigned(const char *str, unsigned long *out)
{
const char * cur = skip_spaces(str);
unsigned long value = 0;
int isempty = 1;
if (cur[0] == '0' && cur[1] == 'x'){
cur += 2;
}
while (*cur != '\0'){
if(*cur >= '0' && *cur <= '9'){
value = (value * 16) + (*cur - '0');
}else if (*cur >= 'a' && *cur <= 'f'){
value = (value * 16) + 10 + (*cur - 'a');
}else if (*cur >= 'A' && *cur <= 'F'){
value = (value * 16) + 10 + (*cur - 'A');
}else{
break;
}
isempty = 0;
++cur;
}
if (isempty){
return (char*)str;
}
*out = value;
return (char*)cur;
}
#define MFMT_DEC_TO_SIGNED(TYPE, NAME) \
static char* \
dec_to_##NAME(const char *str, TYPE *out) \
{ \
long v; \
char *cur = dec_to_signed(str, &v); \
if (cur != str){ \
*out = (TYPE)v; \
} \
return cur; \
}
#define MFMT_DEC_TO_UNSIGNED(TYPE, NAME) \
static char* \
dec_to_##NAME(const char *str, TYPE *out) \
{ \
unsigned long v; \
char *cur = dec_to_unsigned(str, &v); \
if (cur != str){ \
*out = (TYPE)v; \
} \
return cur; \
}
#define MFMT_HEX_TO_SIGNED(TYPE, NAME) \
static char* \
hex_to_##NAME(const char *str, TYPE *out) \
{ \
long v; \
char *cur = hex_to_signed(str, &v); \
if (cur != str){ \
*out = (TYPE)v; \
} \
return cur; \
}
#define MFMT_HEX_TO_UNSIGNED(TYPE, NAME) \
static char* \
hex_to_##NAME(const char *str, TYPE *out) \
{ \
unsigned long v; \
char *cur = hex_to_unsigned(str, &v); \
if (cur != str){ \
*out = (TYPE)v; \
} \
return cur; \
}
/* Returns a pointer after the last written char, or 'str' on error. */
#define MFMT_SIGNED_TO_HEX(TYPE, NAME) \
static char* \
NAME##_to_hex(TYPE val, int uppercase, char padchar, size_t padlen, \
size_t len, char *str) \
{ \
char buf[24]; \
size_t isneg = 0, cnt = 0; \
if (uppercase){ \
uppercase = 'A'; \
}else{ \
uppercase = 'a'; \
} \
if (val < 0){ \
isneg = 1; \
val = -val; \
} \
do{ \
buf[cnt++] = val % 16; \
val = val / 16; \
}while (val != 0); \
if (padlen > isneg + cnt){ \
padlen -= isneg + cnt; \
padlen = (padlen < len ? padlen : len); \
memset(str, padchar, padlen); \
str += padlen; \
len -= padlen; \
} \
if (isneg && len > 0){ \
str[0] = '-'; \
str += 1; \
len -= 1; \
} \
while (cnt-- > 0 && len-- > 0){ \
if (buf[cnt] < 10){ \
*str = buf[cnt] + '0'; \
}else{ \
*str = (buf[cnt] - 10) + uppercase; \
} \
++str; \
} \
return str; \
}
/* Returns a pointer after the last written char, or 'str' on error. */
#define MFMT_SIGNED_TO_DEC(TYPE, NAME) \
static char* \
NAME##_to_dec(TYPE val, char padchar, size_t padlen, \
size_t len, char *str) \
{ \
char buf[24]; \
size_t isneg = 0, cnt = 0; \
if (val < 0){ \
isneg = 1; \
val = -val; \
} \
do{ \
buf[cnt++] = val % 10; \
val = val / 10; \
}while (val != 0); \
if (padlen > isneg + cnt){ \
padlen -= isneg + cnt; \
padlen = (padlen < len ? padlen : len); \
memset(str, padchar, padlen); \
str += padlen; \
len -= padlen; \
} \
if (isneg && len > 0){ \
str[0] = '-'; \
str += 1; \
len -= 1; \
} \
while (cnt-- > 0 && len-- > 0){ \
*str = buf[cnt] + '0'; \
++str; \
} \
return str; \
}
/* Returns a pointer after the last written char, or 'str' on error. */
#define MFMT_UNSIGNED_TO_HEX(TYPE, NAME) \
static char* \
NAME##_to_hex(TYPE val, int uppercase, char padchar, size_t padlen, \
size_t len, char *str) \
{ \
char buf[24]; \
size_t cnt = 0; \
if (uppercase){ \
uppercase = 'A'; \
}else{ \
uppercase = 'a'; \
} \
do{ \
buf[cnt++] = val % 16; \
val = val / 16; \
}while (val != 0); \
if (padlen > cnt){ \
padlen -= cnt; \
padlen = (padlen < len ? padlen : len); \
memset(str, padchar, padlen); \
str += padlen; \
len -= padlen; \
} \
while (cnt-- > 0 && len-- > 0){ \
if (buf[cnt] < 10){ \
*str = buf[cnt] + '0'; \
}else{ \
*str = (buf[cnt] - 10) + uppercase; \
} \
++str; \
} \
return str; \
}
/* Returns a pointer after the last written char, or 'str' on error. */
#define MFMT_UNSIGNED_TO_DEC(TYPE, NAME) \
static char* \
NAME##_to_dec(TYPE val, char padchar, size_t padlen, \
size_t len, char *str) \
{ \
char buf[24]; \
size_t cnt = 0; \
do{ \
buf[cnt++] = val % 10; \
val = val / 10; \
}while (val != 0); \
if (padlen > cnt){ \
padlen -= cnt; \
padlen = (padlen < len ? padlen : len); \
memset(str, padchar, padlen); \
str += padlen; \
len -= padlen; \
} \
while (cnt-- > 0 && len-- > 0){ \
*str = buf[cnt] + '0'; \
++str; \
} \
return str; \
}
MFMT_DEC_TO_SIGNED(int, int)
MFMT_HEX_TO_SIGNED(int, int)
MFMT_SIGNED_TO_DEC(int, int)
MFMT_SIGNED_TO_HEX(int, int)
MFMT_DEC_TO_UNSIGNED(unsigned int, uint)
MFMT_HEX_TO_UNSIGNED(unsigned int, uint)
MFMT_UNSIGNED_TO_DEC(unsigned int, uint)
MFMT_UNSIGNED_TO_HEX(unsigned int, uint)
MFMT_UNSIGNED_TO_HEX(size_t, siz)
static const char*
parse_arg(const char *fmt, const char *str, va_list args)
{
int *intp, intv = 0;
unsigned int *uintp, uintv = 0, width = 0;
char *charp;
const char *cur = str;
fmt = dec_to_uint(fmt, &width);
if (*fmt == 'd'){
cur = dec_to_int(str, &intv);
if (cur != str){
intp = va_arg(args, int*);
*intp = intv;
}
}else if (*fmt == 'u'){
cur = dec_to_uint(str, &uintv);
if (cur != str){
uintp = va_arg(args, unsigned int*);
*uintp = uintv;
}
}else if (*fmt == 'x' || *fmt == 'X'){
cur = hex_to_uint(str, &uintv);
if (cur != str){
uintp = va_arg(args, unsigned int*);
*uintp = uintv;
}
}else if (*fmt == 'c'){
charp = va_arg(args, char*);
if (width == 0){
width = 1;
}
while (cur[0] != '\0' && uintv < width){
charp[uintv] = cur[0];
++cur;
++uintv;
}
}else if (*fmt == 's'){
charp = va_arg(args, char*);
while (cur[0] != '\0' && ! is_space(cur[0]) &&
(width == 0 || uintv < width)){
charp[uintv] = cur[0];
++cur;
++uintv;
}
charp[uintv] = '\0';
}else if (*fmt == '%' && str[0] == '%'){
++cur;
}
return cur;
}
static char*
print_arg(const char *fmt, char *str, size_t len, va_list args)
{
unsigned int uintv, width = 0;
size_t charplen = 0, padlen = 0;
int intv;
char *charp, padchar = (*fmt == '0' ? '0' : ' ');
fmt = dec_to_uint(fmt, &width);
if (*fmt == 'd' || *fmt == 'i'){
intv = va_arg(args, int);
str = int_to_dec(intv, padchar, width, len, str);
}else if (*fmt == 'u'){
uintv = va_arg(args, unsigned int);
str = uint_to_dec(uintv, padchar, width, len, str);
}else if (*fmt == 'x' || *fmt == 'X'){
uintv = va_arg(args, unsigned int);
str = uint_to_hex(uintv, (*fmt == 'X'), padchar, width,
len, str);
}else if (*fmt == 'p'){
charp = (char*)va_arg(args, void*);
str = siz_to_hex((size_t)charp, 0, padchar, width,
len, str);
}else if (*fmt == 'c'){
intv = va_arg(args, int);
if (width > 1){
padlen = (size_t)width - 1;
padlen = (padlen < len ? padlen : len);
memset(str, ' ', padlen);
str += padlen;
len -= padlen;
}
if (len > 0){
str[0] = (char) intv;
str += 1;
len -= 1;
}
}else if (*fmt == 's'){
charp = va_arg(args, char*);
charplen = strlen(charp);
if (width > 0 && (size_t)width > charplen){
padlen = (size_t)width - charplen;
padlen = (padlen < len ? padlen : len);
memset(str, ' ', padlen);
str += padlen;
len -= padlen;
}
charplen = (charplen < len ? charplen : len);
memcpy(str, charp, charplen);
str += charplen;
len -= charplen;
}else if (*fmt == '%'){
str[0] = '%';
++str;
}
return str;
}
/*
* Public functions.
*/
int
sscanf(const char *str, const char *fmt, ...)
{
int ret = 0;
va_list args;
va_start(args, fmt);
while (fmt[0] != '\0' && str[0] != '\0'){
if (fmt[0] == '%'){
const char * tmp = parse_arg(&fmt[1], str, args);
if (tmp == str){
break;
}
if (fmt[1] != '%'){
++ret;
}
++fmt;
while (fmt[0] >= '0' && fmt[0] <= '9'){
++fmt;
}
++fmt;
str = tmp;
}else if (is_space(fmt[0])){
++fmt;
str = skip_spaces(str);
}else if (fmt[0] == str[0]){
++fmt;
++str;
}else{
break;
}
}
va_end(args);
return ret;
}

View File

@ -0,0 +1,97 @@
#include <stdio.h>
#include <stdlib.h>
#define SIZE 10
FILE files[SIZE] = {0};
/*
FILE* fopen(char* str){
FILE* file = &dummy;
while(file->next != NULL){
file = file->next;
}
file->next = malloc(sizeof(*file));
file->next->str = str;
file->next->pos = 0;
file->next->next = NULL;
return file->next;
}
*/
FILE* fopen(char* str){
int i;
for(i=0;i<SIZE;i++){
if(files[i].str == NULL){
break;
}
}
files[i].str = str;
files[i].pos = 0;
return &files[i];
}
size_t fread(void* ptr, size_t size, size_t nmemb, FILE* stream){
char* out = (char*)ptr;
char* str = stream->str;
size_t total = strlen(str);
if(stream->pos == total){
return 0;
}
size_t c = 0;
for(c=0;c<size*nmemb; ){
out[c++] = str[stream->pos++];
if(stream->pos == total){
break;
}
}
return c;
}
/*
void fclose(FILE* stream){
FILE* file = &dummy;
while(file->next != stream){
file = file->next;
}
FILE* tmp = file->next;
file->next = tmp->next;
free(tmp);
}
*/
void fclose(FILE* stream){
int i;
for(i=0;i<SIZE;i++){
if(&files[i] == stream){
break;
}
}
stream->str = NULL;
stream->pos = 0;
}
char *fgets(char *s, int size, FILE *stream){
char* str = stream->str;
size_t total = strlen(str);
size_t c = 0;
char* r = NULL;
while(stream->pos != total){
if(str[stream->pos] == '\n'){
s[c++] = str[stream->pos++];
break;
}else{
s[c++] = str[stream->pos++];
}
}
return r;
}
int getc(FILE* stream){
char* str = stream->str;
size_t total = strlen(str);
if(stream->pos == total){
return EOF;
}else{
return (unsigned char)str[stream->pos++];
}
}

View File

@ -0,0 +1,33 @@
/*
* Format string by inserting blanks.
*/
void
str_fmt(char *p, int size, int fmt)
{
int n, m, len;
len = strlen (p);
switch (fmt) {
case FMT_RJUST:
for (n = size - len; n > 0; n--)
strichr (p, ' ');
break;
case FMT_LJUST:
for (m = size - len; m > 0; m--)
strcat (p, " ");
break;
case FMT_RJUST0:
for (n = size - len; n > 0; n--)
strichr (p, '0');
break;
case FMT_CENTER:
m = (size - len) / 2;
n = size - (len + m);
for (; m > 0; m--)
strcat (p, " ");
for (; n > 0; n--)
strichr (p, ' ');
break;
}
}

View File

@ -0,0 +1,48 @@
/* $Id: strcat.c,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
char *
strcat(char *dst, const char *src)
{
char *d;
if (!dst || !src)
return (dst);
d = dst;
for (; *d; d++);
for (; *src; src++)
*d++ = *src;
*d = 0;
return (dst);
}

View File

@ -0,0 +1,44 @@
/* $Id: strchr.c,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
char *
strchr(const char *p, int c)
{
if (!p)
return (0);
for (; *p; p++)
if (*p == c)
return ((char *)p);
return (0);
}

View File

@ -0,0 +1,11 @@
/*
* Compare strings.
*/
int
strcmp(const char *s1, const char *s2)
{
while (*s1 == *s2++)
if (*s1++ == 0)
return (0);
return (*(const unsigned char *)s1 - *(const unsigned char *)--s2);
}

View File

@ -0,0 +1,36 @@
#include <stdlib.h>
char *
strcpy (char *dstp, const char *srcp)
{
char *dp = dstp;
if (!dstp)
return (0);
*dp = 0;
if (!srcp)
return (dstp);
while ((*dp++ = *srcp++) != 0);
return (dstp);
}
size_t
strlcpy(char *d, const char *s, size_t l)
{
size_t len = l;
if (d == NULL || l == 0)
return 0;
*d = 0;
if (s == NULL)
return 0;
while (--len)
if ((*d++ = *s++) == 0)
break;
if (len == 0)
*d = 0;
len = l - len;
return len;
}

View File

@ -0,0 +1,48 @@
/* $Id: strcspn.c,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
int
strcspn (const char *p, const char *s)
{
int i, j;
for (i = 0; p[i]; i++) {
for (j = 0; s[j]; j++) {
if (s[j] == p[i])
break;
}
if (s[j])
break;
}
return (i);
}

View File

@ -0,0 +1,16 @@
#include <stdlib.h>
char *
strichr(char *p, int c)
{
char *t;
if (p != NULL) {
for(t = p; *t; t++);
for (; t >= p; t--) {
*(t + 1) = *t;
}
*p = c;
}
return (p);
}

View File

@ -0,0 +1,346 @@
#include <string.h>
#include <stdlib.h>
/* *
* strlen - calculate the length of the string @s, not including
* the terminating '\0' character.
* @s: the input string
*
* The strlen() function returns the length of string @s.
* */
size_t
strlen(const char *s) {
size_t cnt = 0;
while (*s ++ != '\0') {
cnt ++;
}
return cnt;
}
/* *
* strnlen - calculate the length of the string @s, not including
* the terminating '\0' char acter, but at most @len.
* @s: the input string
* @len: the max-length that function will scan
*
* Note that, this function looks only at the first @len characters
* at @s, and never beyond @s + @len.
*
* The return value is strlen(s), if that is less than @len, or
* @len if there is no '\0' character among the first @len characters
* pointed by @s.
* */
size_t
strnlen(const char *s, size_t len) {
size_t cnt = 0;
while (cnt < len && *s ++ != '\0') {
cnt ++;
}
return cnt;
}
/* *
* strcpy - copies the string pointed by @src into the array pointed by @dst,
* including the terminating null character.
* @dst: pointer to the destination array where the content is to be copied
* @src: string to be copied
*
* The return value is @dst.
*
* To avoid overflows, the size of array pointed by @dst should be long enough to
* contain the same string as @src (including the terminating null character), and
* should not overlap in memory with @src.
* */
char *
strcpy(char *dst, const char *src) {
#ifdef __HAVE_ARCH_MEM_OPTS
return __strcpy(dst, src);
#else
char *p = dst;
while ((*p ++ = *src ++) != '\0')
/* nothing */;
return dst;
#endif /* __HAVE_ARCH_MEM_OPTS */
}
/* *
* strncpy - copies the first @len characters of @src to @dst. If the end of string @src
* if found before @len characters have been copied, @dst is padded with '\0' until a
* total of @len characters have been written to it.
* @dst: pointer to the destination array where the content is to be copied
* @src: string to be copied
* @len: maximum number of characters to be copied from @src
*
* The return value is @dst
* */
char *
strncpy(char *dst, const char *src, size_t len) {
char *p = dst;
while (len > 0) {
if ((*p = *src) != '\0') {
src ++;
}
p ++, len --;
}
return dst;
}
/* *
* strncmp - compares up to @n characters of the string @s1 to those of the string @s2
* @s1: string to be compared
* @s2: string to be compared
* @n: maximum number of characters to compare
*
* This function starts comparing the first character of each string. If
* they are equal to each other, it continues with the following pairs until
* the characters differ, until a terminating null-character is reached, or
* until @n characters match in both strings, whichever happens first.
* */
int
strncmp(const char *s1, const char *s2, size_t n) {
while (n > 0 && *s1 != '\0' && *s1 == *s2) {
n --, s1 ++, s2 ++;
}
return (n == 0) ? 0 : (int)((unsigned char)*s1 - (unsigned char)*s2);
}
/* *
* strchr - locates first occurrence of character in string
* @s: the input string
* @c: character to be located
*
* The strchr() function returns a pointer to the first occurrence of
* character in @s. If the value is not found, the function returns 'NULL'.
* */
char *
strchr(const char *s, char c) {
while (*s != '\0') {
if (*s == c) {
return (char *)s;
}
s ++;
}
return NULL;
}
/* *
* strfind - locates first occurrence of character in string
* @s: the input string
* @c: character to be located
*
* The strfind() function is like strchr() except that if @c is
* not found in @s, then it returns a pointer to the null byte at the
* end of @s, rather than 'NULL'.
* */
char *
strfind(const char *s, char c) {
while (*s != '\0') {
if (*s == c) {
break;
}
s ++;
}
return (char *)s;
}
/* *
* strtol - converts string to long integer
* @s: the input string that contains the representation of an integer number
* @endptr: reference to an object of type char *, whose value is set by the
* function to the next character in @s after the numerical value. This
* parameter can also be a null pointer, in which case it is not used.
* @base: x
*
* The function first discards as many whitespace characters as necessary until
* the first non-whitespace character is found. Then, starting from this character,
* takes as many characters as possible that are valid following a syntax that
* depends on the base parameter, and interprets them as a numerical value. Finally,
* a pointer to the first character following the integer representation in @s
* is stored in the object pointed by @endptr.
*
* If the value of base is zero, the syntax expected is similar to that of
* integer constants, which is formed by a succession of:
* - An optional plus or minus sign;
* - An optional prefix indicating octal or hexadecimal base ("0" or "0x" respectively)
* - A sequence of decimal digits (if no base prefix was specified) or either octal
* or hexadecimal digits if a specific prefix is present
*
* If the base value is between 2 and 36, the format expected for the integral number
* is a succession of the valid digits and/or letters needed to represent integers of
* the specified radix (starting from '0' and up to 'z'/'Z' for radix 36). The
* sequence may optionally be preceded by a plus or minus sign and, if base is 16,
* an optional "0x" or "0X" prefix.
*
* The strtol() function returns the converted integral number as a long int value.
* */
#if 0
long
strtol(const char *s, char **endptr, int base) {
int neg = 0;
long val = 0;
// gobble initial whitespace
while (*s == ' ' || *s == '\t') {
s ++;
}
// plus/minus sign
if (*s == '+') {
s ++;
}
else if (*s == '-') {
s ++, neg = 1;
}
// hex or octal base prefix
if ((base == 0 || base == 16) && (s[0] == '0' && s[1] == 'x')) {
s += 2, base = 16;
}
else if (base == 0 && s[0] == '0') {
s ++, base = 8;
}
else if (base == 0) {
base = 10;
}
// digits
while (1) {
int dig;
if (*s >= '0' && *s <= '9') {
dig = *s - '0';
}
else if (*s >= 'a' && *s <= 'z') {
dig = *s - 'a' + 10;
}
else if (*s >= 'A' && *s <= 'Z') {
dig = *s - 'A' + 10;
}
else {
break;
}
if (dig >= base) {
break;
}
s ++, val = (val * base) + dig;
// we don't properly detect overflow!
}
if (endptr) {
*endptr = (char *) s;
}
return (neg ? -val : val);
}
#endif
/* *
* memset - sets the first @n bytes of the memory area pointed by @s
* to the specified value @c.
* @s: pointer the the memory area to fill
* @c: value to set
* @n: number of bytes to be set to the value
*
* The memset() function returns @s.
* */
void *
memset(void *s, char c, size_t n) {
#ifdef __HAVE_ARCH_MEM_OPTS
return __memset(s, c, n);
#else
char *p = s;
while (n -- > 0) {
*p ++ = c;
}
return s;
#endif /* __HAVE_ARCH_MEM_OPTS */
}
/* *
* memcpy - copies the value of @n bytes from the location pointed by @src to
* the memory area pointed by @dst.
* @dst pointer to the destination array where the content is to be copied
* @src pointer to the source of data to by copied
* @n: number of bytes to copy
*
* The memcpy() returns @dst.
*
* Note that, the function does not check any terminating null character in @src,
* it always copies exactly @n bytes. To avoid overflows, the size of arrays pointed
* by both @src and @dst, should be at least @n bytes, and should not overlap
* (for overlapping memory area, memmove is a safer approach).
* */
void *
memcpy(void *dst, const void *src, size_t n) {
#ifdef __HAVE_ARCH_MEM_OPTS
return __memcpy(dst, src, n);
#else
const char *s = src;
char *d = dst;
while (n -- > 0) {
*d ++ = *s ++;
}
return dst;
#endif /* __HAVE_ARCH_MEM_OPTS */
}
/* *
* memmove - copies the values of @n bytes from the location pointed by @src to
* the memory area pointed by @dst. @src and @dst are allowed to overlap.
* @dst pointer to the destination array where the content is to be copied
* @src pointer to the source of data to by copied
* @n: number of bytes to copy
*
* The memmove() function returns @dst.
* */
void *
memmove(void *dst, const void *src, size_t n) {
#ifdef __HAVE_ARCH_MEM_OPTS
return __memmove(dst, src, n);
#else
const char *s = src;
char *d = dst;
if (s < d && s + n > d) {
s += n, d += n;
while (n -- > 0) {
*-- d = *-- s;
}
} else {
while (n -- > 0) {
*d ++ = *s ++;
}
}
return dst;
#endif /* __HAVE_ARCH_MEM_OPTS */
}
/* *
* memcmp - compares two blocks of memory
* @v1: pointer to block of memory
* @v2: pointer to block of memory
* @n: number of bytes to compare
*
* The memcmp() functions returns an integral value indicating the
* relationship between the content of the memory blocks:
* - A zero value indicates that the contents of both memory blocks are equal;
* - A value greater than zero indicates that the first byte that does not
* match in both memory blocks has a greater value in @v1 than in @v2
* as if evaluated as unsigned char values;
* - And a value less than zero indicates the opposite.
* */
int
memcmp(const void *v1, const void *v2, size_t n) {
const char *s1 = (const char *)v1;
const char *s2 = (const char *)v2;
while (n -- > 0) {
if (*s1 != *s2) {
return (int)((unsigned char)*s1 - (unsigned char)*s2);
}
s1 ++, s2 ++;
}
return 0;
}
void bzero(void *s, size_t n){
memset(s, 0, n);
}

View File

@ -0,0 +1,17 @@
int
strncmp(const char *s1, const char *s2, size_t n)
{
if (!s1 || !s2)
return (0);
while (n && (*s1 == *s2)) {
if (*s1 == 0)
return (0);
s1++;
s2++;
n--;
}
if (n)
return (*s1 - *s2);
return (0);
}

View File

@ -0,0 +1,14 @@
char *
strncpy(char *dst, const char *src, size_t n)
{
char *d;
if (!dst || !src)
return (dst);
d = dst;
for (; *src && n; d++, src++, n--)
*d = *src;
while (n--)
*d++ = '\0';
return (dst);
}

View File

@ -0,0 +1,51 @@
/* $Id: strspn.c,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
/* return length of initial segment of p that consists entirely of
* characters from s */
int
strspn(const char *p, const char *s)
{
int i, j;
for (i = 0; p[i]; i++) {
for (j = 0; s[j]; j++) {
if (s[j] == p[i])
break;
}
if (!s[j])
break;
}
return (i);
}

View File

@ -0,0 +1,51 @@
/* $Id: strtok.c,v 1.1.1.1 2006/09/14 01:59:06 root Exp $ */
/*
* Copyright (c) 2000-2002 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
char *
strtok(char *p, const char *tok)
{
static char *t; /* XXX */
char *r;
int n;
if (p)
t = p;
r = t + strspn (t, tok);
if (!(n = strcspn (r, tok)))
return (0);
t = r + n;
if (*t)
*t++ = 0;
return (r);
}

View File

@ -0,0 +1,81 @@
#include <stdlib.h>
#define ULONG_MAX 4294967295UL
#define LONG_MAX 2147483647L
#define LONG_MIN (-LONG_MAX-1)
#define isspace(c) (c==0x20)
#define isdigit(c) (((c) >= '0') && ((c) <= '9'))
#define isalpha(c) ( (((c) >= 'A') && ((c) <= 'Z')) || \
(((c) >= 'a') && ((c) <= 'z')) )
#define isupper(c) (c>='A' && c<='Z')
unsigned long
strtoul(const char *nptr,char **endptr,int base)
{
int c;
unsigned long result = 0L;
unsigned long limit;
int negative = 0;
int overflow = 0;
int digit;
while ((c = *nptr) && isspace(c)) /* skip leading white space */
nptr++;
if ((c = *nptr) == '+' || c == '-') { /* handle signs */
negative = (c == '-');
nptr++;
}
if (base == 0) { /* determine base if unknown */
base = 10;
if (*nptr == '0') {
base = 8;
nptr++;
if ((c = *nptr) == 'x' || c == 'X') {
base = 16;
nptr++;
}
}
} else if (base == 16 && *nptr == '0') {
/* discard 0x/0X prefix if hex */
nptr++;
if ((c = *nptr == 'x') || c == 'X')
nptr++;
}
limit = ULONG_MAX / base; /* ensure no overflow */
nptr--; /* convert the number */
while ((c = *++nptr) != 0) {
if (isdigit(c))
digit = c - '0';
else if(isalpha(c))
digit = c - (isupper(c) ? 'A' : 'a') + 10;
else
break;
if (digit < 0 || digit >= base)
break;
if (result > limit)
overflow = 1;
if (!overflow) {
result = base * result;
if (digit > ULONG_MAX - result)
overflow = 1;
else
result += digit;
}
}
if (negative && !overflow) /* BIZARRE, but ANSI says we should do this! */
result = 0L - result;
if (overflow) {
//extern int errno;
//errno = ERANGE;
result = ULONG_MAX;
}
if (endptr != NULL) /* point at tail */
*endptr = (char *)nptr;
return result;
}

View File

@ -0,0 +1,8 @@
void
strtoupper(char *p)
{
if(!p)
return;
for (; *p; p++)
*p = toupper (*p);
}

View File

@ -0,0 +1,4 @@
int testchar()
{
return *(volatile char *)(SERIAL+1);
}

View File

@ -0,0 +1,55 @@
#include <time.h>
unsigned long _get_count()
{
unsigned long _contval;
asm volatile(
"lui $25, 0xbfb0\n\t"
"lw %0,-0x2000($25)\n\t"
:"=r"(_contval)
:
:"$25"
);
return _contval;
}
unsigned long get_count()
{
return _get_count();
}
unsigned long clock_gettime(int sel,struct timespec *tmp)
{
unsigned long n = 0;
n = _get_count();
tmp->tv_nsec = n*(NSEC_PER_USEC/CPU_COUNT_PER_US)%NSEC_PER_USEC;
tmp->tv_usec = (n/CPU_COUNT_PER_US)%USEC_PER_MSEC;
tmp->tv_msec = (n/CPU_COUNT_PER_US/USEC_PER_MSEC)%MSEC_PER_SEC;
tmp->tv_sec = n/CPU_COUNT_PER_US/NSEC_PER_SEC;
printf("clock ns=%d,sec=%d\n",tmp->tv_nsec,tmp->tv_sec);
return 0;
}
unsigned long get_clock()
{
unsigned long n=0;
n=_get_count();
return n;
}
unsigned long get_ns(void)
{
unsigned long n=0;
n = _get_count();
n=n*(NSEC_PER_USEC/CPU_COUNT_PER_US);
return n;
}
unsigned long get_us(void)
{
unsigned long n=0;
n = _get_count();
n=n/CPU_COUNT_PER_US;
return n;
}

View File

@ -0,0 +1,8 @@
int
toupper(int c)
{
if(c>='a' && c<='z')
return c-'a'+'A';
else
return c;
}

View File

@ -0,0 +1,11 @@
void udelay(int us)
{
int count0,count1;
int debug=0;
us *=CPU_COUNT_PER_US;
asm volatile("mfc0 %0,$9":"=r"(count0));
do{
asm volatile("mfc0 %0,$9":"=r"(count1));
}while(count1 -count0<us);
asm volatile("mtc0 %0,$23;"::"r"(debug));
}

View File

@ -0,0 +1,518 @@
#ifdef FLOATINGPT
#define MAX_FCONVERSION 512 /* largest possible real conversion */
#define MAX_EXPT 5 /* largest possible exponent field */
#define MAX_FRACT 39 /* largest possible fraction field */
#define TESTFLAG(x) 0
typedef double rtype;
extern double modf(double, double *);
static void dtoa (char *dbuf, rtype arg, int fmtch, int width, int prec);
#endif
/*
* int vsprintf(d,s,ap)
*/
int
vsprintf (char *d, const char *s, va_list ap)
{
const char *t;
char *p, *dst, tmp[40];
unsigned int n;
int fmt, trunc, haddot, width, base, longlong;
#ifdef FLOATINGPT
double dbl;
#endif
dst = d;
for (; *s;) {
if (*s == '%') {
s++;
fmt = FMT_RJUST;
width = trunc = haddot = longlong = 0;
for (; *s; s++) {
if (strchr ("dobpxXulscefg%", *s))
break;
else if (*s == '-')
fmt = FMT_LJUST;
else if (*s == '0')
fmt = FMT_RJUST0;
else if (*s == '~')
fmt = FMT_CENTER;
else if (*s == '*') {
if (haddot)
trunc = va_arg (ap, int);
else
width = va_arg (ap, int);
} else if (*s >= '1' && *s <= '9') {
for (t = s; isdigit (*s); s++);
strncpy (tmp, t, s - t);
tmp[s - t] = '\0';
atob (&n, tmp, 10);
if (haddot)
trunc = n;
else
width = n;
s--;
} else if (*s == '.')
haddot = 1;
}
if (*s == '%') {
*d++ = '%';
*d = 0;
} else if (*s == 's') {
p = va_arg (ap, char *);
if (p)
strcpy (d, p);
else
strcpy (d, "(null)");
} else if (*s == 'c') {
n = va_arg (ap, int);
*d = n;
d[1] = 0;
} else {
if (*s == 'l') {
if (*++s == 'l') {
longlong = 1;
++s;
}
}
if (strchr ("dobpxXu", *s)) {
if (*s == 'd')
base = -10;
else if (*s == 'u')
base = 10;
else if (*s == 'x' || *s == 'X')
base = 16;
else if(*s == 'p') {
base = 16;
*d++ = '0';
*d++ = 'x';
fmt = FMT_RJUST0;
width = 8;
}
else if (*s == 'o')
base = 8;
else if (*s == 'b')
base = 2;
#ifdef HAVE_QUAD
if (longlong)
llbtoa(d, va_arg (ap, quad_t),
base);
#else
if (longlong)
{
long x=va_arg (ap, long long);
btoa(d, (long)x,
base);
}
#endif
else
btoa(d, va_arg (ap, int), base);
if (*s == 'X')
strtoupper(d);
}
#ifdef FLOATINGPT
else if (strchr ("eEfgG", *s)) {
dbl = va_arg(ap, double);
dtoa (d, dbl, *s, width, trunc);
trunc = 0;
}
#endif
}
if (trunc)
d[trunc] = 0;
if (width)
str_fmt (d, width, fmt);
for (; *d; d++);
s++;
} else
*d++ = *s++;
}
*d = 0;
return (d - dst);
}
#ifdef FLOATINGPT
/*
* Floating point output, cvt() onward lifted from BSD sources:
*
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Chris Torek.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#define to_char(n) ((n) + '0')
#define to_digit(c) ((c) - '0')
#define _isNan(arg) ((arg) != (arg))
static int cvt (rtype arg, int prec, char *signp, int fmtch,
char *startp, char *endp);
static char *round (double fract, int *exp, char *start, char *end,
char ch, char *signp);
static char *exponent(char *p, int exp, int fmtch);
/*
* _finite arg not Infinity or Nan
*/
static int _finite(rtype d)
{
#if ENDIAN == ENDIAN_LITTLE
struct IEEEdp {
unsigned manl:32;
unsigned manh:20;
unsigned exp:11;
unsigned sign:1;
} *ip;
#else
struct IEEEdp {
unsigned sign:1;
unsigned exp:11;
unsigned manh:20;
unsigned manl:32;
} *ip;
#endif
ip = (struct IEEEdp *)&d;
return (ip->exp != 0x7ff);
}
static void dtoa (char *dbuf, rtype arg, int fmtch, int width, int prec)
{
char buf[MAX_FCONVERSION+1], *cp;
char sign;
int size;
if( !_finite(arg) ) {
if( _isNan(arg) )
strcpy (dbuf, "NaN");
else if( arg < 0)
strcpy (dbuf, "-Infinity");
else
strcpy (dbuf, "Infinity");
return;
}
if (prec == 0)
prec = 6;
else if (prec > MAX_FRACT)
prec = MAX_FRACT;
/* leave room for sign at start of buffer */
cp = buf + 1;
/*
* cvt may have to round up before the "start" of
* its buffer, i.e. ``intf("%.2f", (double)9.999);'';
* if the first character is still NUL, it did.
* softsign avoids negative 0 if _double < 0 but
* no significant digits will be shown.
*/
*cp = '\0';
size = cvt (arg, prec, &sign, fmtch, cp, buf + sizeof(buf));
if (*cp == '\0')
cp++;
if (sign)
*--cp = sign, size++;
cp[size] = 0;
memcpy (dbuf, cp, size + 1);
}
static int
cvt(rtype number, int prec, char *signp, int fmtch, char *startp, char *endp)
{
register char *p, *t;
register double fract;
double integer, tmp;
int dotrim, expcnt, gformat;
dotrim = expcnt = gformat = 0;
if (number < 0) {
number = -number;
*signp = '-';
} else
*signp = 0;
fract = modf(number, &integer);
/* get an extra slot for rounding. */
t = ++startp;
/*
* get integer portion of number; put into the end of the buffer; the
* .01 is added for modf(356.0 / 10, &integer) returning .59999999...
*/
for (p = endp - 1; integer; ++expcnt) {
tmp = modf(integer / 10, &integer);
*p-- = to_char((int)((tmp + .01) * 10));
}
switch (fmtch) {
case 'f':
/* reverse integer into beginning of buffer */
if (expcnt)
for (; ++p < endp; *t++ = *p);
else
*t++ = '0';
/*
* if precision required or alternate flag set, add in a
* decimal point.
*/
if (prec || TESTFLAG(ALTERNATE_FORM))
*t++ = '.';
/* if requires more precision and some fraction left */
if (fract) {
if (prec)
do {
fract = modf(fract * 10, &tmp);
*t++ = to_char((int)tmp);
} while (--prec && fract);
if (fract)
startp = round(fract, (int *)NULL, startp,
t - 1, (char)0, signp);
}
for (; prec--; *t++ = '0');
break;
case 'e':
case 'E':
eformat: if (expcnt) {
*t++ = *++p;
if (prec || TESTFLAG(ALTERNATE_FORM))
*t++ = '.';
/* if requires more precision and some integer left */
for (; prec && ++p < endp; --prec)
*t++ = *p;
/*
* if done precision and more of the integer component,
* round using it; adjust fract so we don't re-round
* later.
*/
if (!prec && ++p < endp) {
fract = 0;
startp = round((double)0, &expcnt, startp,
t - 1, *p, signp);
}
/* adjust expcnt for digit in front of decimal */
--expcnt;
}
/* until first fractional digit, decrement exponent */
else if (fract) {
/* adjust expcnt for digit in front of decimal */
for (expcnt = -1;; --expcnt) {
fract = modf(fract * 10, &tmp);
if (tmp)
break;
}
*t++ = to_char((int)tmp);
if (prec || TESTFLAG(ALTERNATE_FORM))
*t++ = '.';
}
else {
*t++ = '0';
if (prec || TESTFLAG(ALTERNATE_FORM))
*t++ = '.';
}
/* if requires more precision and some fraction left */
if (fract) {
if (prec)
do {
fract = modf(fract * 10, &tmp);
*t++ = to_char((int)tmp);
} while (--prec && fract);
if (fract)
startp = round(fract, &expcnt, startp,
t - 1, (char)0, signp);
}
/* if requires more precision */
for (; prec--; *t++ = '0');
/* unless alternate flag, trim any g/G format trailing 0's */
if (gformat && !TESTFLAG(ALTERNATE_FORM)) {
while (t > startp && *--t == '0');
if (*t == '.')
--t;
++t;
}
t = exponent(t, expcnt, fmtch);
break;
case 'g':
case 'G':
/* a precision of 0 is treated as a precision of 1. */
if (!prec)
++prec;
/*
* ``The style used depends on the value converted; style e
* will be used only if the exponent resulting from the
* conversion is less than -4 or greater than the precision.''
* -- ANSI X3J11
*/
if (expcnt > prec || (!expcnt && fract && fract < .0001)) {
/*
* g/G format counts "significant digits, not digits of
* precision; for the e/E format, this just causes an
* off-by-one problem, i.e. g/G considers the digit
* before the decimal point significant and e/E doesn't
* count it as precision.
*/
--prec;
fmtch -= 2; /* G->E, g->e */
gformat = 1;
goto eformat;
}
/*
* reverse integer into beginning of buffer,
* note, decrement precision
*/
if (expcnt)
for (; ++p < endp; *t++ = *p, --prec);
else
*t++ = '0';
/*
* if precision required or alternate flag set, add in a
* decimal point. If no digits yet, add in leading 0.
*/
if (prec || TESTFLAG(ALTERNATE_FORM)) {
dotrim = 1;
*t++ = '.';
}
else
dotrim = 0;
/* if requires more precision and some fraction left */
if (fract) {
if (prec) {
do {
fract = modf(fract * 10, &tmp);
*t++ = to_char((int)tmp);
} while(!tmp && !expcnt);
while (--prec && fract) {
fract = modf(fract * 10, &tmp);
*t++ = to_char((int)tmp);
}
}
if (fract)
startp = round(fract, (int *)NULL, startp,
t - 1, (char)0, signp);
}
/* alternate format, adds 0's for precision, else trim 0's */
if (TESTFLAG(ALTERNATE_FORM))
for (; prec--; *t++ = '0');
else if (dotrim) {
while (t > startp && *--t == '0');
if (*t != '.')
++t;
}
}
return (t - startp);
}
static char *
round(double fract, int *exp, char *start, char *end, char ch, char *signp)
{
double tmp;
if (fract)
(void)modf(fract * 10, &tmp);
else
tmp = to_digit(ch);
if (tmp > 4)
for (;; --end) {
if (*end == '.')
--end;
if (++*end <= '9')
break;
*end = '0';
if (end == start) {
if (exp) { /* e/E; increment exponent */
*end = '1';
++*exp;
}
else { /* f; add extra digit */
*--end = '1';
--start;
}
break;
}
}
/* ``"%.3f", (double)-0.0004'' gives you a negative 0. */
else if (*signp == '-')
for (;; --end) {
if (*end == '.')
--end;
if (*end != '0')
break;
if (end == start)
*signp = 0;
}
return (start);
}
static char *
exponent(char *p, int exp, int fmtch)
{
char *t;
char expbuf[MAX_FCONVERSION];
*p++ = fmtch;
if (exp < 0) {
exp = -exp;
*p++ = '-';
}
else
*p++ = '+';
t = expbuf + MAX_FCONVERSION;
if (exp > 9) {
do {
*--t = to_char(exp % 10);
} while ((exp /= 10) > 9);
*--t = to_char(exp);
for (; t < expbuf + MAX_FCONVERSION; *p++ = *t++);
}
else {
*p++ = '0';
*p++ = to_char(exp);
}
return (p);
}
#endif /* FLOATINGPT */

View File

@ -0,0 +1,24 @@
CC = ${CROSS_COMPILE}gcc
LD = ${CROSS_COMPILE}ld
OBJCOPY = ${CROSS_COMPILE}objcopy
OBJDUMP = ${CROSS_COMPILE}objdump
AR = ${CROSS_COMPILE}ar
AFLAGS = -G 0 -fno-pic -pipe -mno-abicalls -EL -mips1
CFLAGS += -funroll-all-loops -falign-jumps=16 -falign-functions=16 -fgcse-sm -fgcse-las -finline-functions -finline-limit=1000
CFLAGS += -G8 -I ../include
CFLAGS += -static
SRCS = xxx.c
HEADERS = xxx.h
.PHONY:compile link clean
all: compile
echo "job done"
compile: $(OPATH) $(SRCS) $(HEADERS)
$(CC) $(CFLAGS) -c $(SRCS)
clean:
rm -rf *.o

69
resources/project/start.S Normal file
View File

@ -0,0 +1,69 @@
#/* $Id: start.S,v 1.1.1.1 2006/09/14 01:59:08 root Exp $ */
/*
* Copyright (c) 2001 Opsycon AB (www.opsycon.se)
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by Opsycon AB, Sweden.
* 4. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
* OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
*/
#ifndef _KERNEL
#define _KERNEL
#endif
#include <asm/asm.h>
#include <asm/regdef.h>
#include <cpu.h>
#include <cpu_cde.h>
#include <machine.h>
#include <ns16550.h>
#include <asm/context.h>
.set noreorder
.globl _start
.globl start
.globl __main
_start:
start:
disable_trace_cmp_s
disable_num_monitor_s
lui t2,0x0040
mtc0 t2, c0_status
mtc0 zero, c0_cause
la sp, _stack
la gp, _gp
la t1, memory_game #####
li t2, 0x20000000 ###
subu t9, t1, t2 #kseg1 -> kseg0
jr t9 ###
nop #####
.org 0x380
1: b 1b
nop