ICU-1075 udata.c restructured, split into separate files, hopefully making code clearer, dependencies clearer.

Functionality pretty much unchanged.

X-SVN-Rev: 5716
This commit is contained in:
Andy Heninger 2001-09-07 18:42:29 +00:00
parent 9036c7f6ea
commit 412f48860e
8 changed files with 1002 additions and 786 deletions

View file

@ -181,6 +181,10 @@ SOURCE=.\ucln_cmn.c
# End Source File
# Begin Source File
SOURCE=.\ucmndata.c
# End Source File
# Begin Source File
SOURCE=.\ucmp16.c
# End Source File
# Begin Source File
@ -258,6 +262,10 @@ SOURCE=.\udata.c
# End Source File
# Begin Source File
SOURCE=.\udatamem.c
# End Source File
# Begin Source File
SOURCE=.\uhash.c
# End Source File
# Begin Source File
@ -270,6 +278,11 @@ SOURCE=.\uloc.c
# End Source File
# Begin Source File
SOURCE=.\umapfile.c
# ADD CPP /Ze
# End Source File
# Begin Source File
SOURCE=.\umemstrm.c
# End Source File
# Begin Source File
@ -784,6 +797,10 @@ SOURCE=.\ucln_cmn.h
# End Source File
# Begin Source File
SOURCE=.\ucmndata.h
# End Source File
# Begin Source File
SOURCE=.\ucmp16.h
# End Source File
# Begin Source File
@ -928,6 +945,10 @@ InputPath=.\unicode\udata.h
# End Source File
# Begin Source File
SOURCE=.\udatamem.h
# End Source File
# Begin Source File
SOURCE=.\uhash.h
# End Source File
# Begin Source File
@ -986,6 +1007,10 @@ InputPath=.\unicode\umachine.h
# End Source File
# Begin Source File
SOURCE=.\umapfile.h
# End Source File
# Begin Source File
SOURCE=.\umemstrm.h
# End Source File
# Begin Source File

View file

@ -0,0 +1,223 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************
/*----------------------------------------------------------------------------------
*
* UCommonData An abstract interface for dealing with ICU Common Data Files.
* ICU Common Data Files are a grouping of a number of individual
* data items (resources, converters, tables, anything) into a
* single file or dll. The combined format includes a table of
* contents for locating the individual items by name.
*
* Two formats for the table of contents are supported, which is
* why there is an abstract inteface involved.
*
*/
#include "unicode/utypes.h"
#include "unicode/udata.h"
#include "cstring.h"
#include "ucmndata.h"
#include "udatamem.h"
/*----------------------------------------------------------------------------------*
* *
* Pointer TOCs. TODO: This form of table-of-contents should be removed because *
* DLLs must be relocated on loading to correct the pointer values *
* and this operation makes shared memory mapping of the data *
* much less likely to work. *
* *
*----------------------------------------------------------------------------------*/
typedef struct {
const char *entryName;
const DataHeader *pHeader;
} PointerTOCEntry;
/*----------------------------------------------------------------------------------*
* *
* entry point lookup implementations *
* *
*----------------------------------------------------------------------------------*/
static uint32_t offsetTOCEntryCount(const UDataMemory *pData) {
uint32_t count = *(const uint32_t *)pData->toc;
return count;
}
static const DataHeader *
offsetTOCLookupFn(const UDataMemory *pData,
const char *tocEntryName,
UErrorCode *pErrorCode) {
if(pData->toc!=NULL) {
const char *base=(const char *)pData->toc;
uint32_t *toc=(uint32_t *)pData->toc;
uint32_t start, limit, number;
/* perform a binary search for the data in the common data's table of contents */
start=0;
limit=*toc++; /* number of names in this table of contents */
if (limit == 0) { /* Stub common data library used during build is empty. */
return NULL;
}
while(start<limit-1) {
number=(start+limit)/2;
if(uprv_strcmp(tocEntryName, base+toc[2*number])<0) {
limit=number;
} else {
start=number;
}
}
if(uprv_strcmp(tocEntryName, base+toc[2*start])==0) {
/* found it */
#ifdef UDATA_DEBUG
fprintf(stderr, "Found: %p\n",(base+toc[2*start+1]));
#endif
return (const DataHeader *)(base+toc[2*start+1]);
} else {
#ifdef UDATA_DEBUG
fprintf(stderr, "Not found.\n");
#endif
return NULL;
}
} else {
#ifdef UDATA_DEBUG
fprintf(stderr, "returning header\n");
#endif
return pData->pHeader;
}
}
static uint32_t pointerTOCEntryCount(const UDataMemory *pData) {
uint32_t count = *(const uint32_t *)pData->toc;
return count;
}
static const DataHeader *pointerTOCLookupFn(const UDataMemory *pData,
const char *tocEntryName,
UErrorCode *pErrorCode) {
#ifdef UDATA_DEBUG
fprintf(stderr, "ptrTOC[%p] looking for %s/%s\n",
pData,
tocEntryName,dllEntryName);
#endif
if(pData->toc!=NULL) {
const PointerTOCEntry *toc=(const PointerTOCEntry *)((const uint32_t *)pData->toc+2);
uint32_t start, limit, number;
/* perform a binary search for the data in the common data's table of contents */
start=0;
limit=*(const uint32_t *)pData->toc; /* number of names in this table of contents */
#ifdef UDATA_DEBUG
fprintf(stderr, " # of ents: %d\n", limit);
fflush(stderr);
#endif
if (limit == 0) { /* Stub common data library used during build is empty. */
return NULL;
}
while(start<limit-1) {
number=(start+limit)/2;
if(uprv_strcmp(tocEntryName, toc[number].entryName)<0) {
limit=number;
} else {
start=number;
}
}
if(uprv_strcmp(tocEntryName, toc[start].entryName)==0) {
/* found it */
#ifdef UDATA_DEBUG
fprintf(stderr, "FOUND: %p\n",
normalizeDataPointer(toc[start].pHeader));
#endif
return normalizeDataPointer(toc[start].pHeader);
} else {
#ifdef UDATA_DEBUG
fprintf(stderr, "NOT found\n");
#endif
return NULL;
}
} else {
#ifdef UDATA_DEBUG
fprintf(stderr, "Returning header\n");
#endif
return pData->pHeader;
}
}
static commonDataFuncs CmnDFuncs = {offsetTOCLookupFn, offsetTOCEntryCount};
static commonDataFuncs ToCPFuncs = {pointerTOCLookupFn, pointerTOCEntryCount};
/*----------------------------------------------------------------------*
* *
* checkCommonData Validate the format of a common data file. *
* Fill in the virtual function ptr based on TOC type *
* If the data is invalid, close the UDataMemory *
* and set the appropriate error code. *
* *
*----------------------------------------------------------------------*/
void checkCommonData(UDataMemory *udm, UErrorCode *err) {
if (U_FAILURE(*err)) {
return;
}
if(!(udm->pHeader->dataHeader.magic1==0xda &&
udm->pHeader->dataHeader.magic2==0x27 &&
udm->pHeader->info.isBigEndian==U_IS_BIG_ENDIAN &&
udm->pHeader->info.charsetFamily==U_CHARSET_FAMILY)
) {
/* header not valid */
*err=U_INVALID_FORMAT_ERROR;
}
else if (udm->pHeader->info.dataFormat[0]==0x43 &&
udm->pHeader->info.dataFormat[1]==0x6d &&
udm->pHeader->info.dataFormat[2]==0x6e &&
udm->pHeader->info.dataFormat[3]==0x44 &&
udm->pHeader->info.formatVersion[0]==1
) {
/* dataFormat="CmnD" */
udm->vFuncs = &CmnDFuncs;
udm->toc=(const char *)udm->pHeader+udm->pHeader->dataHeader.headerSize;
}
else if(udm->pHeader->info.dataFormat[0]==0x54 &&
udm->pHeader->info.dataFormat[1]==0x6f &&
udm->pHeader->info.dataFormat[2]==0x43 &&
udm->pHeader->info.dataFormat[3]==0x50 &&
udm->pHeader->info.formatVersion[0]==1
) {
/* dataFormat="ToCP" */
udm->vFuncs = &ToCPFuncs;
udm->toc=(const char *)udm->pHeader+udm->pHeader->dataHeader.headerSize;
}
else {
/* dataFormat not recognized */
*err=U_INVALID_FORMAT_ERROR;
}
if (U_FAILURE(*err)) {
/* If the data is no good and we memory-mapped it ourselves,
* close the memory mapping so it doesn't leak. Note that this has
* no effect on non-memory mapped data, other than clearing fields in udm.
*/
udata_close(udm);
}
}

View file

@ -0,0 +1,81 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************
/*----------------------------------------------------------------------------------
*
* UCommonData An abstract interface for dealing with ICU Common Data Files.
* ICU Common Data Files are a grouping of a number of individual
* data items (resources, converters, tables, anything) into a
* single file or dll. The combined format includes a table of
* contents for locating the individual items by name.
*
* Two formats for the table of contents are supported, which is
* why there is an abstract inteface involved.
*
* These functions are part of the ICU internal implementation, and
* are not inteded to be used directly by applications.
*/
#ifndef __UCMNDATA_H__
#define __UCMNDATA_H__
#include "unicode/udata.h"
#include "umapfile.h"
#define COMMON_DATA_NAME U_ICUDATA_NAME
typedef struct {
uint16_t headerSize;
uint8_t magic1;
uint8_t magic2;
} MappedData;
typedef struct {
MappedData dataHeader;
UDataInfo info;
} DataHeader;
/*
* "Virtual" functions for data lookup.
* To call one, given a UDataMemory *p, the code looks like this:
* p->vFuncs.Lookup(p, tocEntryName, pErrorCode);
* (I sure do wish this was written in C++, not C)
*/
typedef const DataHeader *
(* LookupFn)(const UDataMemory *pData,
const char *tocEntryName,
UErrorCode *pErrorCode);
typedef uint32_t
(* NumEntriesFn)(const UDataMemory *pData);
typedef struct {
LookupFn Lookup;
NumEntriesFn NumEntries;
} commonDataFuncs;
/*
* Functions to check whether a UDataMemory refers to memory containing
* a recognizable header and table of contents a Common Data Format
*
* If a valid header and TOC are found,
* set the CommonDataFuncs function dispatch vector in the UDataMemory
* to point to the right functions for the TOC type.
* otherwise
* set an errorcode.
*/
void checkCommonData(UDataMemory *pData, UErrorCode *pErrorCode);
#endif

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,99 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************
/*----------------------------------------------------------------------------------
*
* UDataMemory A class-like struct that serves as a handle to a piece of memory
* that contains some ICU data (resource, converters, whatever.)
*
* When an application opens ICU data (with udata_open, for example,
* a UDataMemory * is returned.
*
*----------------------------------------------------------------------------------*/
#include "unicode/utypes.h"
#include "unicode/putil.h"
#include "cmemory.h"
#include "cstring.h"
#include "unicode/udata.h"
#include "udatamem.h"
void UDataMemory_init(UDataMemory *This) {
uprv_memset(This, 0, sizeof(UDataMemory));
}
void UDatamemory_assign(UDataMemory *dest, UDataMemory *source) {
/* UDataMemory Assignment. Destination UDataMemory must be initialized first. */
UBool mallocedFlag = dest->heapAllocated;
uprv_memcpy(dest, source, sizeof(UDataMemory));
dest->heapAllocated = mallocedFlag;
}
UDataMemory *UDataMemory_createNewInstance(UErrorCode *pErr) {
UDataMemory *This;
if (U_FAILURE(*pErr)) {
return NULL;
}
This = uprv_malloc(sizeof(UDataMemory));
if (This == NULL) {
*pErr = U_MEMORY_ALLOCATION_ERROR; }
else {
UDataMemory_init(This);
This->heapAllocated = TRUE;
}
return This;
}
const DataHeader *
normalizeDataPointer(const void *p) {
/* allow the data to be optionally prepended with an alignment-forcing double value */
const DataHeader *pdh = (const DataHeader *)p;
if(pdh==NULL || (pdh->dataHeader.magic1==0xda && pdh->dataHeader.magic2==0x27)) {
return pdh;
} else {
return (const DataHeader *)((const double *)p+1);
}
}
void UDataMemory_setData (UDataMemory *This, const void *dataAddr) {
This->pHeader = normalizeDataPointer(dataAddr);
}
U_CAPI void U_EXPORT2
udata_close(UDataMemory *pData) {
if(pData!=NULL) {
uprv_unmapFile(pData);
if(pData->heapAllocated ) {
uprv_free(pData);
} else {
UDataMemory_init(pData);
}
}
}
U_CAPI const void * U_EXPORT2
udata_getMemory(UDataMemory *pData) {
if(pData!=NULL && pData->pHeader!=NULL) {
return (char *)(pData->pHeader)+pData->pHeader->dataHeader.headerSize;
} else {
return NULL;
}
}
UBool UDataMemory_isLoaded(UDataMemory *This) {
return This->pHeader != NULL;
}

View file

@ -0,0 +1,47 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************/
/*----------------------------------------------------------------------------------
*
* UDataMemory A class-like struct that serves as a handle to a piece of memory
* that contains some ICU data (resource, converters, whatever.)
*
* When an application opens ICU data (with udata_open, for example,
* a UDataMemory * is returned.
*
*----------------------------------------------------------------------------------*/
#ifndef __UDATAMEM_H__
#define __UDATAMEM_H__
#include "ucmndata.h"
typedef struct UDataMemory {
void *map; /* Handle, or whatever. OS dependent. */
/* Only set if a close operation should unmap the */
/* associated data. */
const void *mapAddr; /* For mapped or allocated memory, the start addr. */
/* Needed to allow unmapping. */
commonDataFuncs *vFuncs; /* Function Pointers for accessing TOC */
const void *toc; /* For common memory, to find pieces within. */
const DataHeader *pHeader; /* Header. For common data, header is at top of file */
UBool heapAllocated; /* True if this UDataMemObject is on the heap */
/* and thus needs to be deleted when closed. */
} UDataMemory;
UDataMemory *UDataMemory_createNewInstance(UErrorCode *pErr);
void UDatamemory_assign (UDataMemory *dest, UDataMemory *source);
void UDataMemory_init (UDataMemory *This);
UBool UDataMemory_isLoaded(UDataMemory *This);
void UDataMemory_setData (UDataMemory *This, const void *dataAddr);
const DataHeader *normalizeDataPointer(const void *p);
#endif

View file

@ -0,0 +1,379 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************
/*----------------------------------------------------------------------------------
*
* Memory mapped file wrappers for use by the ICU Data Implementation
* All of the platform-specific implementation for mapping data files
* is here. The rest of the ICU Data implementation uses only the
* wrapper functions.
*
*----------------------------------------------------------------------------------*/
#include "unicode/utypes.h"
#include "udatamem.h"
#include "umapfile.h"
/* memory-mapping base definitions ------------------------------------------ */
#define MAP_WIN32 1
#define MAP_POSIX 2
#define MAP_FILE_STREAM 3
#define MAP_390DLL 4
#ifdef WIN32
# define WIN32_LEAN_AND_MEAN
# define NOGDI
# define NOUSER
# define NOSERVICE
# define NOIME
# define NOMCX
# include <windows.h>
typedef HANDLE MemoryMap;
# define IS_MAP(map) ((map)!=NULL)
# define MAP_IMPLEMENTATION MAP_WIN32
/* ### Todo: auto detect mmap(). Until then, just add your platform here. */
#elif HAVE_MMAP || defined(U_LINUX) || defined(POSIX) || defined(U_SOLARIS) || defined(AIX) || defined(HPUX) || defined(OS390) || defined(PTX)
typedef size_t MemoryMap;
# define IS_MAP(map) ((map)!=0)
# include <unistd.h>
# include <sys/mman.h>
# include <sys/stat.h>
# include <fcntl.h>
# ifndef MAP_FAILED
# define MAP_FAILED ((void*)-1)
# endif
# define MAP_IMPLEMENTATION MAP_POSIX
#elif OS390
/* No memory mapping for 390 batch mode. Fake it using dll loading. */
# include <dll.h>
# define MAP_IMPLEMENTATION MAP_390DLL
#else /* unknown platform, no memory map implementation: use FileStream/uprv_malloc() instead */
# include "filestrm.h"
typedef void *MemoryMap;
# define IS_MAP(map) ((map)!=NULL)
# define MAP_IMPLEMENTATION MAP_FILE_STREAM
#endif
/*----------------------------------------------------------------------------------*
* *
* Memory Mapped File support. Platform dependent implementation of functions *
* used by the rest of the implementation. *
* *
*----------------------------------------------------------------------------------*/
#if MAP_IMPLEMENTATION==MAP_WIN32
UBool
uprv_mapFile(
UDataMemory *pData, /* Fill in with info on the result doing the mapping. */
/* Output only; any original contents are cleared. */
const char *path /* File path to be opened/mapped */
)
{
HANDLE map;
HANDLE file;
UDataMemory_init(pData); /* Clear the output struct. */
/* open the input file */
file=CreateFile(path, GENERIC_READ, FILE_SHARE_READ, NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL|FILE_FLAG_RANDOM_ACCESS, NULL);
if(file==INVALID_HANDLE_VALUE) {
return FALSE;
}
/* create an unnamed Windows file-mapping object for the specified file */
map=CreateFileMapping(file, NULL, PAGE_READONLY, 0, 0, NULL);
CloseHandle(file);
if(map==NULL) {
return FALSE;
}
/* map a view of the file into our address space */
pData->pHeader=(const DataHeader *)MapViewOfFile(map, FILE_MAP_READ, 0, 0, 0);
if(pData->pHeader==NULL) {
CloseHandle(map);
return FALSE;
}
pData->map=map;
return TRUE;
}
void
uprv_unmapFile(UDataMemory *pData) {
if(pData!=NULL && pData->map!=NULL) {
UnmapViewOfFile(pData->pHeader);
CloseHandle(pData->map);
pData->pHeader=NULL;
pData->map=NULL;
}
}
#elif MAP_IMPLEMENTATION==MAP_POSIX
static UBool
uprv_mapFile(UDataMemory *pData, const char *path) {
int fd;
int length;
struct stat mystat;
const void *data;
UDataMemory_init(pData); /* Clear the output struct. */
/* determine the length of the file */
if(stat(path, &mystat)!=0 || mystat.st_size<=0) {
return FALSE;
}
length=mystat.st_size;
/* open the file */
fd=open(path, O_RDONLY);
if(fd==-1) {
return FALSE;
}
/* get a view of the mapping */
#ifndef HPUX
data=mmap(0, length, PROT_READ, MAP_SHARED, fd, 0);
#else
data=mmap(0, length, PROT_READ, MAP_PRIVATE, fd, 0);
#endif
close(fd); /* no longer needed */
if(data==MAP_FAILED) {
# ifdef UDATA_DEBUG
perror("mmap");
# endif
return FALSE;
}
# ifdef UDATA_DEBUG
fprintf(stderr, "mmap of %s [%d bytes] succeeded, -> 0x%X\n", path, length, data);
fflush(stderr);
# endif
pData->map=length;
pData->pHeader=(const DataHeader *)data;
pData->mapAddr = data;
return TRUE;
}
static void
uprv_unmapFile(UDataMemory *pData) {
if(pData!=NULL && pData->map>0) {
if(munmap((void *)pData->mapAddr, pData->map)==-1) {
# ifdef UDATA_DEBUG
perror("munmap");
# endif
}
pData->pHeader=NULL;
pData->map=0;
pData->mapAddr=NULL;
}
}
#elif MAP_IMPLEMENTATION==MAP_FILE_STREAM
static UBool
uprv_mapFile(UDataMemory *pData, const char *path) {
FileStream *file;
int32_t fileLength;
void *p;
UDataMemory_init(pData); /* Clear the output struct. */
/* open the input file */
file=T_FileStream_open(path, "rb");
if(file==NULL) {
return FALSE;
}
/* get the file length */
fileLength=T_FileStream_size(file);
if(T_FileStream_error(file) || fileLength<=20) {
T_FileStream_close(file);
return FALSE;
}
/* allocate the data structure */
p=uprv_malloc(fileLength);
if(p==NULL) {
T_FileStream_close(file);
return FALSE;
}
/* read the file */
if(fileLength!=T_FileStream_read(file, p, fileLength)) {
uprv_free(p);
T_FileStream_close(file);
return FALSE;
}
T_FileStream_close(file);
pData->map=p;
pData->pHeader=(const DataHeader *)p;
pData->mapAddr=p;
return TRUE;
}
static void
uprv_unmapFile(UDataMemory *pData) {
if(pData!=NULL && pData->map!=NULL) {
uprv_free(pData->map);
pData->map = NULL;
pData->mapAddr = NULL;
pData->pHeader = NULL;
}
}
#elif MAP_IMPLEMENTATION==MAP_390DLL
/* 390 specific Library Loading.
* This is the only platform left that dynamically loads an ICU Data Library.
* All other platforms use .data files when dynamic loading is required, but
* this turn out to be awkward to support in 390 batch mode.
*
* The idea here is to hide the fact that 390 is using dll loading from the
* rest of ICU, and make it look like there is file loading happening.
*
*/
uprv_mapFile(UDataMemory *pData, const char *path) {
/* TODO: turn the path into a dll name, try to load it,
* if successful, set the the pHeader field of the UDataMemory
* to the data address.
*
* (If path has a ".dat" extension, take it off and add on whatever
* the standard shared library extension is?)
*/
}
void uprv_unmapFile(UDataMemory *pData) {
if(pData!=NULL && pData->map!=NULL) {
/* TODO: whatever. Doesn't really need to do anything. */
}
}
# define RTLD_LAZY 0
# define RTLD_GLOBAL 0
static void *dlopen(const char *filename, int flag) {
dllhandle *handle;
# ifdef UDATA_DEBUG
fprintf(stderr, "dllload: %s ", filename);
# endif
handle=dllload(filename);
# ifdef UDATA_DEBUG
fprintf(stderr, " -> %08X\n", handle );
# endif
return handle;
}
static void *dlsym(void *h, const char *symbol) {
void *val=0;
val=dllqueryvar((dllhandle*)h,symbol);
# ifdef UDATA_DEBUG
fprintf(stderr, "dllqueryvar(%08X, %s) -> %08X\n", h, symbol, val);
# endif
return val;
}
static int dlclose(void *handle) {
# ifdef UDATA_DEBUG
fprintf(stderr, "dllfree: %08X\n", handle);
# endif
return dllfree((dllhandle*)handle);
}
/* TODO: the following code is just a mish-mash of pieces from the
* previous OS390 data library loading code that might be useful
* in putting together something that works.
*/
#if 0
Library lib;
inBasename=U_ICUDATA_NAME"_390";
suffix=strcpy_returnEnd(basename, inBasename);
uprv_strcpy(suffix, LIB_SUFFIX);
if (uprv_isOS390BatchMode()) {
/* ### hack: we still need to get u_getDataDirectory() fixed
for OS/390 (batch mode - always return "//"? )
and this here straightened out with LIB_PREFIX and LIB_SUFFIX (both empty?!)
This is probably due to the strange file system on OS/390. It's more like
a database with short entry names than a typical file system. */
if (s390dll) {
lib=LOAD_LIBRARY("//IXMICUD1", "//IXMICUD1");
}
else {
/* U_ICUDATA_NAME should always have the correct name */
/* 390port: BUT FOR BATCH MODE IT IS AN EXCEPTION ... */
/* 390port: THE NEXT LINE OF CODE WILL NOT WORK !!!!! */
/*lib=LOAD_LIBRARY("//" U_ICUDATA_NAME, "//" U_ICUDATA_NAME);*/
lib=LOAD_LIBRARY("//IXMICUDA", "//IXMICUDA"); /*390port*/
}
}
lib=LOAD_LIBRARY(pathBuffer, basename);
if(!IS_LIBRARY(lib) && basename!=pathBuffer) {
/* try basename only next */
lib=LOAD_LIBRARY(basename, basename);
}
if(IS_LIBRARY(lib)) {
/* we have a data DLL - what kind of lookup do we need here? */
char entryName[100];
const DataHeader *pHeader;
*basename=0;
}
checkCommonData(&tData, pErrorCode);
if (U_SUCCESS(*pErrorCode)) {
/* Don't close the old data - someone might be using it
* May need to change the global to be a pointer rather than a static struct
* to get a clean switch-over.
*/
setCommonICUData(&tData);
}
umtx_unlock(NULL);
return TRUE; /* SUCCESS? */
#endif
#else
# error MAP_IMPLEMENTATION is set incorrectly
#endif

View file

@ -0,0 +1,32 @@
/*
******************************************************************************
*
* Copyright (C) 1999-2001, International Business Machines
* Corporation and others. All Rights Reserved.
*
******************************************************************************
/*----------------------------------------------------------------------------------
*
* Memory mapped file wrappers for use by the ICU Data Implementation
*
* Porting note: The implementation of these functions is very platform specific.
* Not all platforms can do real memory mapping. Those that can't
* still must implement these functions, getting the data into memory using
* whatever means are available.
*
* These functions are part of the ICU internal implementation, and
* are not inteded to be used directly by applications.
*
*----------------------------------------------------------------------------------*/
#ifndef __UMAPFILE_H__
#define __UMAPFILE_H__
typedef struct UDataMemory UDataMemory;
UBool uprv_mapFile(UDataMemory *pdm, const char *path);
void uprv_unmapFile(UDataMemory *pData);
#endif