Subversion Repositories Kolibri OS

Compare Revisions

Regard whitespace Rev 4873 → Rev 4874

/contrib/sdk/sources/newlib/libc/crt/crt3.c
0,0 → 1,65
/*
* crt1.c
* This file has no copyright assigned and is placed in the Public Domain.
* This file is a part of the mingw-runtime package.
* No warranty is given; refer to the file DISCLAIMER within the package.
*
* Source code for the startup proceedures used by all programs. This code
* is compiled to make crt1.o, which should be located in the library path.
*
*/
 
/* Hide the declaration of _fmode with dllimport attribute in stdlib.h to
avoid problems with older GCC. */
 
#include <newlib.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
 
/*
typedef void (*ctp)();
static void __do_global_ctors ()
{
extern int __CTOR_LIST__;
int *c = &__CTOR_LIST__;
c++;
while (*c)
{
ctp d = (ctp)*c;
(d)();
c++;
}
}
*/
 
void *load_libc();
//void __main (){};
 
void* get_entry_point(void *raw);
 
void _pei386_runtime_relocator (void){};
 
void __attribute__((noreturn))
__crt_startup (void)
{
struct app_hdr *header;
void *img;
void __attribute__((noreturn)) (*entry)(void *img);
 
// _pei386_runtime_relocator();
 
img = load_libc();
 
if(img == NULL)
{
asm ("int $0x40" ::"a"(-1));
};
 
entry = get_entry_point(img);
entry(img);
}
 
 
 
/contrib/sdk/sources/newlib/libc/crt/emutls.c
0,0 → 1,217
/* TLS emulation.
Copyright (C) 2006, 2008, 2009 Free Software Foundation, Inc.
Contributed by Jakub Jelinek <jakub@redhat.com>.
 
This file is part of GCC.
 
GCC is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 3, or (at your option) any later
version.
 
GCC is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
 
Under Section 7 of GPL version 3, you are granted additional
permissions described in the GCC Runtime Library Exception, version
3.1, as published by the Free Software Foundation.
 
You should have received a copy of the GNU General Public License and
a copy of the GCC Runtime Library Exception along with this program;
see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
<http://www.gnu.org/licenses/>. */
 
 
#include <stdlib.h>
#include <malloc.h>
#include <errno.h>
#include <gthr.h>
 
void *tls_alloc(void);
void __mutex_lock(volatile int *val);
 
 
static inline void yield(void)
{
__asm__ __volatile__(
"int $0x40"
::"a"(68), "b"(1));
};
 
int __gthread_once (__gthread_once_t *once, void (*func) (void))
{
if (once == NULL || func == NULL)
return EINVAL;
 
if (! once->done)
{
if(++once->started == 0)
{
(*func) ();
once->done = 1;
}
else
{
/* Another thread is currently executing the code, so wait for it
to finish; yield the CPU in the meantime. If performance
does become an issue, the solution is to use an Event that
we wait on here (and set above), but that implies a place to
create the event before this routine is called. */
while (! once->done)
yield();
}
}
return 0;
}
 
 
#define __GTHREAD_ONCE_INIT {0, -1}
 
typedef unsigned int word __attribute__((mode(word)));
typedef unsigned int pointer __attribute__((mode(pointer)));
 
struct __emutls_object
{
word size;
word align;
union {
pointer offset;
void *ptr;
} loc;
void *templ;
};
 
struct __emutls_array
{
pointer size;
void **data[];
};
 
void *__emutls_get_address (struct __emutls_object *);
void __emutls_register_common (struct __emutls_object *, word, word, void *);
 
static __gthread_mutex_t emutls_mutex;
static __gthread_key_t emutls_key;
static pointer emutls_size;
 
static void emutls_destroy (void *ptr)
{
struct __emutls_array *arr = ptr;
pointer size = arr->size;
pointer i;
 
for (i = 0; i < size; ++i)
{
if (arr->data[i])
free (arr->data[i][-1]);
}
free (ptr);
};
 
static void emutls_init (void)
{
if (__gthread_key_create (&emutls_key, emutls_destroy) != 0)
abort ();
}
 
static void *emutls_alloc (struct __emutls_object *obj)
{
void *ptr;
void *ret;
 
/* We could use here posix_memalign if available and adjust
emutls_destroy accordingly. */
if (obj->align <= sizeof (void *))
{
ptr = malloc (obj->size + sizeof (void *));
if (ptr == NULL)
abort ();
((void **) ptr)[0] = ptr;
ret = ptr + sizeof (void *);
}
else
{
ptr = malloc (obj->size + sizeof (void *) + obj->align - 1);
if (ptr == NULL)
abort ();
ret = (void *) (((pointer) (ptr + sizeof (void *) + obj->align - 1))
& ~(pointer)(obj->align - 1));
((void **) ret)[-1] = ptr;
}
 
if (obj->templ)
memcpy (ret, obj->templ, obj->size);
else
memset (ret, 0, obj->size);
 
return ret;
}
 
void * __emutls_get_address (struct __emutls_object *obj)
{
pointer offset = obj->loc.offset;
 
if (__builtin_expect (offset == 0, 0))
{
static __gthread_once_t once = __GTHREAD_ONCE_INIT;
__gthread_once (&once, emutls_init);
__gthread_mutex_lock (&emutls_mutex);
offset = obj->loc.offset;
if (offset == 0)
{
offset = ++emutls_size;
obj->loc.offset = offset;
}
__gthread_mutex_unlock (&emutls_mutex);
}
 
struct __emutls_array *arr = __gthread_getspecific (emutls_key);
if (__builtin_expect (arr == NULL, 0))
{
pointer size = offset + 32;
arr = calloc (size + 1, sizeof (void *));
if (arr == NULL)
abort ();
arr->size = size;
__gthread_setspecific (emutls_key, (void *) arr);
}
else if (__builtin_expect (offset > arr->size, 0))
{
pointer orig_size = arr->size;
pointer size = orig_size * 2;
if (offset > size)
size = offset + 32;
arr = realloc (arr, (size + 1) * sizeof (void *));
if (arr == NULL)
abort ();
arr->size = size;
memset (arr->data + orig_size, 0,
(size - orig_size) * sizeof (void *));
__gthread_setspecific (emutls_key, (void *) arr);
}
 
void *ret = arr->data[offset - 1];
if (__builtin_expect (ret == NULL, 0))
{
ret = emutls_alloc (obj);
arr->data[offset - 1] = ret;
}
return ret;
}
 
 
void __emutls_register_common (struct __emutls_object *obj,
word size, word align, void *templ)
{
if (obj->size < size)
{
obj->size = size;
obj->templ = NULL;
}
if (obj->align < align)
obj->align = align;
if (templ && size == obj->size)
obj->templ = templ;
}
/contrib/sdk/sources/newlib/libc/crt/pseudo-reloc.c
0,0 → 1,213
/* pseudo-reloc.c
 
Contributed by Egor Duda <deo@logos-m.ru>
Modified by addition of runtime_pseudo_reloc version 2
by Kai Tietz <kai.tietz@onevision.com>
 
THIS SOFTWARE IS NOT COPYRIGHTED
 
This source code is offered for use in the public domain. You may
use, modify or distribute it freely.
 
This code is distributed in the hope that it will be useful but
WITHOUT ANY WARRANTY. ALL WARRENTIES, EXPRESS OR IMPLIED ARE HEREBY
DISCLAMED. This includes but is not limited to warrenties of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
*/
 
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
 
extern char __RUNTIME_PSEUDO_RELOC_LIST__;
extern char __RUNTIME_PSEUDO_RELOC_LIST_END__;
extern char _image_base__;
 
void _pei386_runtime_relocator (void);
 
/* v1 relocation is basically:
* *(base + .target) += .addend
* where (base + .target) is always assumed to point
* to a DWORD (4 bytes).
*/
typedef struct {
uint32_t addend;
uint32_t target;
} runtime_pseudo_reloc_item_v1;
 
/* v2 relocation is more complex. In effect, it is
* *(base + .target) += *(base + .sym) - (base + .sym)
* with care taken in both reading, sign extension, and writing
* because .flags may indicate that (base + .target) may point
* to a BYTE, WORD, DWORD, or QWORD (w64).
*/
typedef struct {
uint32_t sym;
uint32_t target;
uint32_t flags;
} runtime_pseudo_reloc_item_v2;
 
typedef struct {
uint32_t magic1;
uint32_t magic2;
uint32_t version;
} runtime_pseudo_reloc_v2;
 
#define RP_VERSION_V1 0
#define RP_VERSION_V2 1
 
static void
do_pseudo_reloc (void * start, void * end, void * base)
{
ptrdiff_t addr_imp, reldata;
ptrdiff_t reloc_target = (ptrdiff_t) ((char *)end - (char*)start);
runtime_pseudo_reloc_v2 *v2_hdr = (runtime_pseudo_reloc_v2 *) start;
runtime_pseudo_reloc_item_v2 *r;
 
/* A valid relocation list will contain at least one entry, and
* one v1 data structure (the smallest one) requires two DWORDs.
* So, if the relocation list is smaller than 8 bytes, bail.
*/
if (reloc_target < 8)
return;
 
/* Check if this is the old pseudo relocation version. */
/* There are two kinds of v1 relocation lists:
* 1) With a (v2-style) version header. In this case, the
* first entry in the list is a 3-DWORD structure, with
* value:
* { 0, 0, RP_VERSION_V1 }
* In this case, we skip to the next entry in the list,
* knowing that all elements after the head item can
* be cast to runtime_pseudo_reloc_item_v1.
* 2) Without a (v2-style) version header. In this case, the
* first element in the list IS an actual v1 relocation
* record, which is two DWORDs. Because there will never
* be a case where a v1 relocation record has both
* addend == 0 and target == 0, this case will not be
* confused with the prior one.
* All current binutils, when generating a v1 relocation list,
* use the second (e.g. original) form -- that is, without the
* v2-style version header.
*/
if (reloc_target >= 12
&& v2_hdr->magic1 == 0 && v2_hdr->magic2 == 0
&& v2_hdr->version == RP_VERSION_V1)
{
/* We have a list header item indicating that the rest
* of the list contains v1 entries. Move the pointer to
* the first true v1 relocation record. By definition,
* that v1 element will not have both addend == 0 and
* target == 0 (and thus, when interpreted as a
* runtime_pseudo_reloc_v2, it will not have both
* magic1 == 0 and magic2 == 0).
*/
v2_hdr++;
}
 
if (v2_hdr->magic1 != 0 || v2_hdr->magic2 != 0)
{
/*************************
* Handle v1 relocations *
*************************/
runtime_pseudo_reloc_item_v1 * o;
for (o = (runtime_pseudo_reloc_item_v1 *) v2_hdr;
o < (runtime_pseudo_reloc_item_v1 *)end;
o++)
{
uint32_t newval;
reloc_target = (ptrdiff_t) base + o->target;
newval = (*((uint32_t*) reloc_target)) + o->addend;
*(uint32_t*)reloc_target = newval;
}
return;
}
 
/* If we got this far, then we have relocations of version 2 or newer */
 
/* Check if this is a known version. */
if (v2_hdr->version != RP_VERSION_V2)
{
// printf(" Unknown pseudo relocation protocol version %d.\n",
// (int) v2_hdr->version);
return;
}
 
/*************************
* Handle v2 relocations *
*************************/
 
/* Walk over header. */
r = (runtime_pseudo_reloc_item_v2 *) &v2_hdr[1];
 
for (; r < (runtime_pseudo_reloc_item_v2 *) end; r++)
{
/* location where new address will be written */
reloc_target = (ptrdiff_t) base + r->target;
 
/* get sym pointer. It points either to the iat entry
* of the referenced element, or to the stub function.
*/
addr_imp = (ptrdiff_t) base + r->sym;
addr_imp = *((ptrdiff_t *) addr_imp);
 
/* read existing relocation value from image, casting to the
* bitsize indicated by the 8 LSBs of flags. If the value is
* negative, manually sign-extend to ptrdiff_t width. Raise an
* error if the bitsize indicated by the 8 LSBs of flags is not
* supported.
*/
switch ((r->flags & 0xff))
{
case 8:
reldata = (ptrdiff_t) (*((unsigned char *)reloc_target));
if ((reldata & 0x80) != 0)
reldata |= ~((ptrdiff_t) 0xff);
break;
case 16:
reldata = (ptrdiff_t) (*((unsigned short *)reloc_target));
if ((reldata & 0x8000) != 0)
reldata |= ~((ptrdiff_t) 0xffff);
break;
case 32:
reldata = (ptrdiff_t) (*((unsigned int *)reloc_target));
break;
default:
reldata=0;
// printf(" Unknown pseudo relocation bit size %d.\n",
// (int) (r->flags & 0xff));
break;
}
 
/* Adjust the relocation value */
reldata -= ((ptrdiff_t) base + r->sym);
reldata += addr_imp;
 
/* Write the new relocation value back to *reloc_target */
switch ((r->flags & 0xff))
{
case 8:
*(uint8_t*)reloc_target = (uint8_t)reldata;
break;
case 16:
*(uint16_t*)reloc_target = (uint16_t)reldata;
break;
case 32:
*(uint32_t*)reloc_target = (uint32_t)reldata;
break;
}
}
}
 
void
_pei386_runtime_relocator (void)
{
static int was_init = 0;
if (was_init)
return;
++was_init;
do_pseudo_reloc (&__RUNTIME_PSEUDO_RELOC_LIST__,
&__RUNTIME_PSEUDO_RELOC_LIST_END__,
&_image_base__);
}
/contrib/sdk/sources/newlib/libc/crt/dllstart.c
0,0 → 1,27
 
extern void _pei386_runtime_relocator (void);
 
typedef void (*ctp)();
static void __do_global_ctors ()
{
extern int __CTOR_LIST__;
int *c = &__CTOR_LIST__;
c++;
while (*c)
{
ctp d = (ctp)*c;
(d)();
c++;
}
}
 
int __attribute__((externally_visible)) DllStartup(void *module, int reason)
{
if(reason == 1)
{
_pei386_runtime_relocator();
__do_global_ctors();
};
 
return 1;
};
/contrib/sdk/sources/newlib/libc/crt/chkstk.S
0,0 → 1,61
 
.global ___chkstk
.global ___chkstk_ms
.global __alloca
 
.section .text
 
#.def ___chkstk; .scl 2; .type 32; .endef
#.def ___chkstk_ms; .scl 2; .type 32; .endef
#.def __alloca; .scl 2; .type 32; .endef
 
___chkstk:
__alloca:
pushl %ecx /* save temp */
leal 8(%esp), %ecx /* point past return addr */
subl %eax, %ecx
cmpl %fs:8, %ecx # check low stack limit
jb 1f
 
movl %esp, %eax /* save old stack pointer */
movl %ecx, %esp /* decrement stack */
movl (%eax), %ecx /* recover saved temp */
movl 4(%eax), %eax /* recover return address */
 
/* Push the return value back. Doing this instead of just
jumping to %eax preserves the cached call-return stack
used by most modern processors. */
pushl %eax
ret
1:
int3 #trap to debugger
.ascii "Stack overflow"
 
 
___chkstk_ms:
pushl %ecx /* save temp */
pushl %eax
cmpl $0x1000, %eax /* > 4k ?*/
leal 12(%esp), %ecx /* point past return addr */
jb 2f
 
1:
subl $0x1000, %ecx /* yes, move pointer down 4k*/
cmpl %fs:8, %ecx /* check low stack limit */
jb 3f
 
orl $0x0, (%ecx) /* probe there */
subl $0x1000, %eax /* decrement count */
cmpl $0x1000, %eax
ja 1b /* and do it again */
 
2:
subl %eax, %ecx
orl $0x0, (%ecx) /* less than 4k, just peek here */
 
popl %eax
popl %ecx
ret
3:
int3 #trap to debugger
.ascii "Stack overflow"
/contrib/sdk/sources/newlib/libc/crt/cpu_features.c
0,0 → 1,72
 
#include "cpu_features.h"
 
/* level 1 edx bits */
#define EDX_CX8 (1 << 8) /* CMPXCHG8B */
#define EDX_CMOV (1 << 15)
#define EDX_MMX (1 << 23)
#define EDX_FXSR (1 << 24) /* FXSAVE and FXRSTOR */
#define EDX_SSE (1 << 25)
#define EDX_SSE2 (1 << 26)
 
/* level 1 ecx bits */
#define ECX_SSE3 (1 << 0)
#define ECX_CX16 (1 << 13) /* CMPXCHG16B */
 
/* extended level 0x80000001 edx bits */
#define EDX_3DNOW (1 << 31)
#define EDX_3DNOWP (1 << 30)
#define EDX_LM (1 << 29) /*LONG MODE */
 
#define __cpuid(level,a,b,c,d) \
__asm__ __volatile__ ("cpuid;" \
: "=a" (a), "=b" (b), "=c" (c), "=d" (d)\
: "0" (level))
 
/* Combine the different cpuid flags into a single bitmap. */
 
unsigned int __cpu_features = 0;
 
void __cpu_features_init (void)
{
unsigned int eax, ebx, ecx, edx;
 
__cpuid (0, eax, ebx, ecx, edx);
if (eax == 0)
return;
 
__cpuid (1, eax, ebx, ecx, edx);
 
if (edx & EDX_CX8)
__cpu_features |= _CRT_CMPXCHG8B;
if (edx & EDX_CMOV)
__cpu_features |= _CRT_CMOV;
 
if (edx & EDX_MMX)
__cpu_features |= _CRT_MMX;
if (edx & EDX_FXSR)
__cpu_features |= _CRT_FXSR;
if (edx & EDX_SSE)
__cpu_features |= _CRT_SSE;
if (edx & EDX_SSE2)
__cpu_features |= _CRT_SSE2;
 
 
if (ecx & ECX_SSE3)
__cpu_features |= _CRT_SSE3;
if (ecx & ECX_CX16)
__cpu_features |= _CRT_CMPXCHG16B;
 
__cpuid (0x80000000, eax, ebx, ecx, edx);
if (eax < 0x80000001)
return;
__cpuid (0x80000001, eax, ebx, ecx, edx);
if (edx & EDX_3DNOW)
__cpu_features |= _CRT_3DNOW;
if (edx & EDX_3DNOWP)
__cpu_features |= _CRT_3DNOWP;
 
return;
}
 
 
/contrib/sdk/sources/newlib/libc/crt/cpu_features.h
0,0 → 1,21
#ifndef _CPU_FEATURES_H
#define _CPU_FEATURES_H
 
#define _CRT_CMPXCHG8B 0x0001
#define _CRT_CMOV 0x0002
#define _CRT_MMX 0x0004
#define _CRT_FXSR 0x0008
#define _CRT_SSE 0x0010
#define _CRT_SSE2 0x0020
#define _CRT_SSE3 0x0040
#define _CRT_CMPXCHG16B 0x0080
#define _CRT_3DNOW 0x0100
#define _CRT_3DNOWP 0x0200
 
extern unsigned int __cpu_features;
 
/* Currently we use this in fpenv functions */
#define __HAS_SSE __cpu_features & _CRT_SSE
 
 
#endif
/contrib/sdk/sources/newlib/libc/crt/crt1.c
0,0 → 1,137
/*
* crt1.c
* This file has no copyright assigned and is placed in the Public Domain.
* This file is a part of the mingw-runtime package.
* No warranty is given; refer to the file DISCLAIMER within the package.
*
* Source code for the startup proceedures used by all programs. This code
* is compiled to make crt1.o, which should be located in the library path.
*
*/
 
/* Hide the declaration of _fmode with dllimport attribute in stdlib.h to
avoid problems with older GCC. */
 
#include <newlib.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <sys/kos_io.h>
 
#include "cpu_features.h"
 
 
/* NOTE: The code for initializing the _argv, _argc, and environ variables
* has been moved to a separate .c file which is included in both
* crt1.c and dllcrt1.c. This means changes in the code don't have to
* be manually synchronized, but it does lead to this not-generally-
* a-good-idea use of include. */
 
 
extern char __cmdline[];
extern char __pgmname[];
 
extern int main (int, char **, char **);
 
int _errno;
int _fmode;
 
char __appcwd[1024];
int __appcwdlen;
 
int _argc;
char **_argv;
 
static char *arg[2];
 
void _exit(int __status) __attribute__((noreturn));
 
 
char * __libc_getenv(const char *name)
{
return NULL;
}
 
void __main (){};
 
struct app_hdr
{
char banner[8];
int version;
int start;
int iend;
int memsize;
int stacktop;
char *cmdline;
char *path;
};
 
typedef void (*ctp)();
static void __do_global_ctors ()
{
extern int __CTOR_LIST__;
int *c = &__CTOR_LIST__;
c++;
while (*c)
{
ctp d = (ctp)*c;
(d)();
c++;
}
}
 
void __attribute__((noreturn))
__crt_startup (void)
{
int nRet;
struct app_hdr *header;
 
 
init_global_reent();
 
/*
* Initialize floating point unit.
*/
__cpu_features_init (); /* Do we have SSE, etc.*/
// _fpreset (); /* Supplied by the runtime library. */
 
__do_global_ctors();
 
__appcwdlen = strrchr(&__pgmname[0], '/') - &__pgmname[0] + 1;
__appcwdlen = __appcwdlen > 1023 ? 1023 : __appcwdlen;
memcpy(__appcwd, &__pgmname, __appcwdlen);
__appcwd[__appcwdlen] = 0;
 
set_cwd(__appcwd);
 
arg[0] = &__pgmname[0];
 
if( __cmdline[0] != 0)
{
_argc = 2;
arg[1] = &__cmdline[0];
} else _argc = 1;
 
_argv = arg;
 
/*
* Sets the default file mode.
* If _CRT_fmode is set, also set mode for stdin, stdout
* and stderr, as well
* NOTE: DLLs don't do this because that would be rude!
*/
// _mingw32_init_fmode ();
 
 
nRet = main (_argc, _argv, NULL);
 
/*
* Perform exit processing for the C library. This means
* flushing output and calling 'atexit' registered functions.
*/
exit (nRet);
}
 
 
 
/contrib/sdk/sources/newlib/libc/crt/crt2.c
0,0 → 1,22
#include <newlib.h>
 
void init_reent();
 
void __attribute__((noreturn))
__thread_startup (int (*entry)(void*), void *param,
void *stacklow, void *stackhigh)
{
int retval;
 
__asm__ __volatile__( // save stack limits
"movl %0, %%fs:8 \n\t" // use TLS
"movl %1, %%fs:12 \n\t"
::"r"(stacklow), "r"(stackhigh));
 
init_reent(); // initialize thread reentry structure
 
retval = entry(param); // call user thread function
 
_exit(retval);
};
 
/contrib/sdk/sources/newlib/libc/crt/crt_amz.S
0,0 → 1,24
 
 
.global __start
.global ___main
.global _DllMainCRTStartup
 
 
.section .init
 
.def __start; .scl 2; .type 32; .endef
.def _DllMainCRTStartup; .scl 2; .type 32; .endef
 
.align 4
__start:
_DllMainCRTStartup:
 
call __pei386_runtime_relocator
jmp _main
 
.align 4
___main:
ret
 
 
/contrib/sdk/sources/newlib/libc/crt/crtbegin.c
0,0 → 1,15
 
extern void _pei386_runtime_relocator (void);
 
int DllStartup(void *module, int reason)
{
_pei386_runtime_relocator();
return 1;
};
 
void ___dll_start ()
 
{
_pei386_runtime_relocator();
 
}
/contrib/sdk/sources/newlib/libc/crt/crtdll.c
0,0 → 1,125
 
#include <_ansi.h>
#include <reent.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <unistd.h>
#include <setjmp.h>
#include <sys/kos_io.h>
 
struct app_hdr
{
char banner[8];
int version;
int start;
int iend;
int memsize;
int stacktop;
char *cmdline;
char *path;
int reserved;
void *__idata_start;
void *__idata_end;
int (*main)(int argc, char **argv, char **envp);
};
 
int _argc;
char **_argv;
 
 
void* get_entry_point(void *raw);
int (*entry)(int, char **, char **);
 
void init_loader(void *libc_image);
 
 
void init_reent();
 
jmp_buf loader_env;
 
void __attribute__((noreturn))
__thread_startup (int (*entry)(void*), void *param,
void *stacklow, void *stackhigh)
{
int retval;
 
asm volatile ( "xchgw %bx, %bx");
 
__asm__ __volatile__( // save stack limits
"movl %0, %%fs:8 \n\t" // use TLS
"movl %1, %%fs:12 \n\t"
::"r"(stacklow), "r"(stackhigh));
 
init_reent(); // initialize thread reentry structure
 
retval = entry(param); // call user thread function
 
_exit(retval);
};
 
char * __libc_getenv(const char *name)
{
return NULL;
}
 
void _pei386_runtime_relocator (void);
int link_app();
 
char __appcwd[1024];
int __appcwdlen;
char* __appenv;
int __appenv_size;
 
static char *arg[2];
 
extern char _tls_map[128];
 
void __attribute__((noreturn))
libc_crt_startup (void *libc_base)
{
struct app_hdr *header = NULL;
 
int len;
char *p;
 
void *my_app;
int retval = 0;
 
_pei386_runtime_relocator();
 
memset(_tls_map, 0xFF, 32*4);
_tls_map[0] = 0xE0;
init_reent();
__initPOSIXHandles();
 
// __appenv = load_file("/sys/system.env", &__appenv_size);
 
init_loader(libc_base);
 
if( link_app() == 0)
goto done;
 
__appcwdlen = strrchr(header->path, '/') - header->path;
__appcwdlen = __appcwdlen > 1022 ? 1022 : __appcwdlen;
memcpy(__appcwd, header->path, __appcwdlen);
set_cwd(__appcwd);
 
arg[0] = header->path;
 
if( header->cmdline[0] != 0)
{
_argc = 2;
arg[1] = header->cmdline;
}
else _argc = 1;
 
_argv = arg;
 
retval = header->main(_argc, _argv, NULL);
done:
exit (retval);
}
 
 
/contrib/sdk/sources/newlib/libc/crt/exit.S
0,0 → 1,20
 
 
.section .text
 
.global __exit
.global __Exit
 
 
.align 4
__exit:
__Exit:
movl 4(%esp), %edx #store exit code
movl $68, %eax
movl $13, %ebx
movl %fs:8, %ecx
int $0x40 #destroy stack
 
movl $-1, %eax
int $0x40 #terminate thread
 
/contrib/sdk/sources/newlib/libc/crt/i386mach.h
0,0 → 1,76
/* This file was based on the modified setjmp.S performed by
* Joel Sherill (joel@OARcorp.com) which specified the use
* of the __USER_LABEL_PREFIX__ and __REGISTER_PREFIX__ macros.
**
** This file is distributed WITHOUT ANY WARRANTY; without even the implied
** warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
*/
 
/* These are predefined by new versions of GNU cpp. */
#ifndef __USER_LABEL_PREFIX__
#define __USER_LABEL_PREFIX__ _
#endif
 
#define __REG_PREFIX__ %
/* ANSI concatenation macros. */
#define CONCAT1(a, b) CONCAT2(a, b)
#define CONCAT2(a, b) a##b
/* Use the right prefix for global labels. */
#define SYM(x) CONCAT1(__USER_LABEL_PREFIX__, x)
/* Use the right prefix for registers. */
#define REG(x) CONCAT1(__REG_PREFIX__, x)
#define eax REG(eax)
#define ebx REG(ebx)
#define ecx REG(ecx)
#define edx REG(edx)
#define esi REG(esi)
#define edi REG(edi)
#define ebp REG(ebp)
#define esp REG(esp)
 
#define st0 REG(st)
#define st1 REG(st(1))
#define st2 REG(st(2))
#define st3 REG(st(3))
#define st4 REG(st(4))
#define st5 REG(st(5))
#define st6 REG(st(6))
#define st7 REG(st(7))
 
#define ax REG(ax)
#define bx REG(bx)
#define cx REG(cx)
#define dx REG(dx)
 
#define ah REG(ah)
#define bh REG(bh)
#define ch REG(ch)
#define dh REG(dh)
 
#define al REG(al)
#define bl REG(bl)
#define cl REG(cl)
#define dl REG(dl)
 
#define mm1 REG(mm1)
#define mm2 REG(mm2)
#define mm3 REG(mm3)
#define mm4 REG(mm4)
#define mm5 REG(mm5)
#define mm6 REG(mm6)
#define mm7 REG(mm7)
 
#ifdef _I386MACH_NEED_SOTYPE_FUNCTION
#define SOTYPE_FUNCTION(sym) .type SYM(sym),@function
#else
#define SOTYPE_FUNCTION(sym)
#endif
 
/contrib/sdk/sources/newlib/libc/crt/opendial.S
0,0 → 1,149
format MS COFF
 
public _get_moviefile
 
section '.text' align 16
 
align 4
getprocaddress:
mov edx, [esp + 8] ; hlib
xor eax, eax
test edx, edx ; If hlib = 0 then goto .end
jz .end
 
.next:
cmp [edx], dword 0 ; If end of export table then goto .end
jz .end
 
xor eax, eax
mov esi, [edx]
mov edi, [esp + 4] ; name
 
.next_:
lodsb
scasb
jne .fail
or al, al
jnz .next_
jmp .ok
.fail:
add edx, 8
jmp .next
 
.ok: ; return address
mov eax, [edx + 4]
.end:
ret 8
 
 
 
align 8
_get_moviefile:
 
pushad
mov eax, 68
mov ebx, 19
mov ecx, sz_proc_lib
int 0x40
mov [proclib], eax
test eax, eax
jz .fail
 
push [proclib]
push sz_OpenDialog_init
call getprocaddress
mov [opendialog_init], eax
 
push dword[proclib]
push sz_OpenDialog_start
call getprocaddress
mov [opendialog_start], eax
 
mov eax, 68
mov ebx, 12
mov ecx, 4096*3
int 0x40
 
mov [od.procinfo], eax
 
add eax, 1024
mov [od.filename_area], eax
 
add eax, 3072
mov [od.opendir_path], eax
 
add eax, 4096
mov [od.openfile_path], eax
 
push od
call [opendialog_init]
 
mov eax, [od.openfile_path]
mov [eax], byte 0 ; end of ASCIIZ-string(may be don't need?)
 
push od
call [opendialog_start]
 
popad
mov eax, [od.openfile_path]; selected filePath
 
ret
.fail:
xor eax, eax
ret
 
align 4
fake_on_redraw:
ret
 
section '.rdata' align 16
 
sz_proc_lib db "/rd/1/lib/proc_lib.obj",0
sz_OpenDialog_init db "OpenDialog_init",0
sz_OpenDialog_start db "OpenDialog_start",0
sz_com_area_name db "FFFFFFFF_open_dialog",0
sz_dir_default_path db "/rd/1",0
sz_start_path db "/rd/1/File managers/opendial",0
 
 
section '.data' align 16
 
od:
.mode dd 0
.procinfo dd 0
.com_area_name dd sz_com_area_name
.com_area dd 0
.opendir_path dd 0
.dir_default_path dd sz_dir_default_path
.start_path dd sz_start_path
.draw_window dd fake_on_redraw
.status dd 0
.openfile_path dd 0
.filename_area dd 0
.filter_area dd filefilter
.x_size dw 512
.x_start dw 512
.y_size dw 512
.y_start dw 512
 
filefilter:
dd filefilter.end - filefilter
db 'avi',0
db 'flv',0
db 'mov',0
db 'mpg',0
db 'mpeg',0
db 'mkv',0
db 'mp4',0
db 'webm',0
db 'wmv',0
.end:
db 0
 
 
section '.bss' align 16
 
proclib dd ?
opendialog_init dd ?
opendialog_start dd ?
 
/contrib/sdk/sources/newlib/libc/crt/setjmp.S
0,0 → 1,89
/* This is file is a merger of SETJMP.S and LONGJMP.S */
/*
* This file was modified to use the __USER_LABEL_PREFIX__ and
* __REGISTER_PREFIX__ macros defined by later versions of GNU cpp by
* Joel Sherrill (joel@OARcorp.com)
* Slight change: now includes i386mach.h for this (Werner Almesberger)
*
* Copyright (C) 1991 DJ Delorie
* All rights reserved.
*
* Redistribution and use in source and binary forms is permitted
* provided that the above copyright notice and following paragraph are
* duplicated in all such forms.
*
* This file is distributed WITHOUT ANY WARRANTY; without even the implied
* warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
*/
 
/*
** jmp_buf:
** eax ebx ecx edx esi edi ebp esp eip
** 0 4 8 12 16 20 24 28 32
*/
 
#include "i386mach.h"
 
.global SYM (setjmp)
.global SYM (longjmp)
SOTYPE_FUNCTION(setjmp)
SOTYPE_FUNCTION(longjmp)
 
.def _setjmp; .scl 2; .type 32; .endef
 
SYM (setjmp):
 
pushl ebp
movl esp,ebp
 
pushl edi
movl 8 (ebp),edi
 
movl eax,0 (edi)
movl ebx,4 (edi)
movl ecx,8 (edi)
movl edx,12 (edi)
movl esi,16 (edi)
 
movl -4 (ebp),eax
movl eax,20 (edi)
 
movl 0 (ebp),eax
movl eax,24 (edi)
 
movl esp,eax
addl $12,eax
movl eax,28 (edi)
 
movl 4 (ebp),eax
movl eax,32 (edi)
 
popl edi
movl $0,eax
leave
ret
 
.def _longjmp; .scl 2; .type 32; .endef
 
SYM (longjmp):
pushl ebp
movl esp,ebp
 
movl 8(ebp),edi /* get jmp_buf */
movl 12(ebp),eax /* store retval in j->eax */
movl eax,0(edi)
 
movl 24(edi),ebp
 
movl 28(edi),esp
 
pushl 32(edi)
 
movl 0(edi),eax
movl 4(edi),ebx
movl 8(edi),ecx
movl 12(edi),edx
movl 16(edi),esi
movl 20(edi),edi
 
ret
/contrib/sdk/sources/newlib/libc/crt/start.S
0,0 → 1,46
 
.section .init
 
.global __start
 
#tls:0 pid process id
#tls:4 tid reserved for thread slot
#tls:8 thread's stack low limit
#tls:12 thread's stack high limit
#tls:16 reseved for libc
 
.align 4
__start:
movl $68, %eax
movl $12, %ebx
lea __size_of_stack_reserve__, %ecx
addl $4095, %ecx #load stack size
andl $-4096, %ecx #align to page granularity
int $0x40 #and allocate
testl %eax, %eax
jz 1f
 
addl %eax, %ecx
movl %eax, %fs:8
movl %ecx, %fs:12 #save stack base - low limit
#save stack top - high limit
movl %ecx, %esp #reload stack
 
subl $1024, %esp
 
movl $9, %eax
movl %esp, %ebx
movl $-1, %ecx
int $0x40
 
movl 30(%ebx), %eax
movl %eax, %fs:0 #save pid
 
addl $1024, %esp
 
jmp ___crt_startup
1:
int3 #trap to debugger
 
.ascii "No enough memory for stack allocation"
 
/contrib/sdk/sources/newlib/libc/crt/thread.S
0,0 → 1,48
 
.global _create_thread
.global ___thread_startup
 
.section .text
 
.def _create_thread; .scl 2; .type 32; .endef
 
.align 4
_create_thread:
#.thr_proc equ esp+8
#.param equ esp+12
#.stack_size equ esp+16
 
pushl %ebx
 
movl $68, %eax
movl $12, %ebx
movl 16(%esp), %ecx #[.stack_size]
addl $4095, %ecx
andl $-4096, %ecx
movl %ecx, 16(%esp) #save stack size
int $0x40
testl %eax, %eax
jz 1f
 
leal -20(%eax,%ecx), %edx
 
movl 8(%esp), %ebx #[.thr_proc]
mov %ebx, 4(%edx)
 
movl 12(%esp), %ebx #[.param]
movl %ebx, 8(%edx)
 
addl %eax, %ecx
movl %eax, 12(%edx) #stack low limit
movl %ecx, 16(%edx) #stack high limit
 
movl $51, %eax
movl $1, %ebx
lea ___thread_startup , %ecx
int $0x40
popl %ebx
ret
1:
notl %eax
popl %ebx
ret
/contrib/sdk/sources/newlib/libc/crt/tls.S
0,0 → 1,48
 
 
.section .text
 
.global _tls_alloc
.global __tls_map
 
.align 4
_tls_alloc:
 
pushl $tls_mutex
call ___mutex_lock
popl %eax
 
movl tls_map_start, %edx
.align 4
.test:
bsfl (%edx), %eax
jnz .done
 
add $4, %edx
cmpl $128+__tls_map, %edx
jb .test
 
xorl %eax, %eax
mov %eax, tls_mutex
ret
 
.done:
btrl %eax, (%edx)
movl %edx, tls_map_start
movl $0, tls_mutex
 
subl $__tls_map, %edx
leal (%eax, %edx, 8), %eax
shll $2, %eax
ret
 
.section .data
 
tls_mutex: .long(0)
tls_map_start: .long(__tls_map)
 
.section .bss
 
.align 16
 
__tls_map: .space 128