📄 semsingl.c
字号:
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: WHEN YOU FIGURE OUT WHAT THIS FILE DOES, PLEASE
* DESCRIBE IT HERE!
*
****************************************************************************/
#include <unistd.h>
#include <fcntl.h>
#include <string.h>
#include <errno.h>
#include "wresall.h"
#include "rcmem.h"
#include "errors.h"
#include "global.h"
#include "ytab.gh"
#include "semantic.h"
#include "semsingl.h"
#include "reserr.h"
#include "depend.h"
#include "scan.h"
#include "iortns.h"
/**** forward references ****/
static void AddIconResource( WResID * name, ResMemFlags flags,
ResMemFlags group_flags, char * filename );
static void AddCursorResource( WResID * name, ResMemFlags flags,
ResMemFlags group_flags, char * filename );
static void AddBitmapResource( WResID * name, ResMemFlags, char * filename );
static void AddFontResources( WResID * name, ResMemFlags, char * filename );
/* MS changed the default purity for ICON and CURSOR resources from rc */
/* version 30 to 31. Note: the ICON_GROUP and CURSOR_GROUP resources */
/* still have the same purity */
#define CUR_ICON_PURITY_30 MEMFLAG_PURE
#define CUR_ICON_PURITY_31 0 /* impure */
extern void SemAddMessageTable( WResID *name, ScanString *filename ) {
/********************************************************************/
ResLocation start;
if( CmdLineParms.TargetOS == RC_TARGET_OS_WIN32 ) {
start = SemCopyRawFile( filename->string );
RcMemFree( filename->string );
RcMemFree( filename );
SemAddResourceFree( name, WResIDFromNum( (long)RT_MESSAGETABLE ),
MEMFLAG_MOVEABLE | MEMFLAG_PURE, start );
} else {
RcError( ERR_NT_KEYWORD, SemTokenToString( Y_MESSAGETABLE ) );
ErrorHasOccured = TRUE;
RcMemFree( name );
RcMemFree( filename->string );
RcMemFree( filename );
}
}
extern void SemAddSingleLineResource( WResID * name, uint_8 type,
FullMemFlags * fullflags, char * filename )
/***************************************************************/
{
ResMemFlags flags;
ResMemFlags group_flags;
ResMemFlags purity_option; /* used for icon and cursor resoures */
char full_filename[ _MAX_PATH ];
if (ErrorHasOccured) {
RcMemFree( name );
RcMemFree( filename );
return;
}
if (CmdLineParms.VersionStamp == VERSION_30_STAMP) {
purity_option = CUR_ICON_PURITY_30;
} else {
purity_option = CUR_ICON_PURITY_31;
}
RcFindResource( filename, full_filename );
if (full_filename[0] == '\0') {
RcError( ERR_CANT_FIND_FILE, filename );
goto HANDLE_ERROR;
}
if( AddDependency( full_filename ) ) goto HANDLE_ERROR;
switch (type) {
case Y_ICON:
if (fullflags != NULL) {
SemCheckMemFlags( fullflags, 0,
MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE,
purity_option );
flags = fullflags->flags;
SemCheckMemFlags( fullflags, 0,
MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE,
MEMFLAG_PURE );
group_flags = fullflags->flags;
} else {
flags = MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE| purity_option;
group_flags = MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE|MEMFLAG_PURE;
}
AddIconResource( name, flags, group_flags, full_filename );
break;
case Y_CURSOR:
if (fullflags != NULL) {
SemCheckMemFlags( fullflags, 0,
MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE,
purity_option );
flags = fullflags->flags;
SemCheckMemFlags( fullflags, 0,
MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE,
MEMFLAG_PURE );
group_flags = fullflags->flags;
} else {
flags = MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE| purity_option;
group_flags = MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE|MEMFLAG_PURE;
}
AddCursorResource( name, flags, group_flags, full_filename );
break;
case Y_BITMAP:
if (fullflags != NULL) {
SemCheckMemFlags( fullflags, 0, MEMFLAG_MOVEABLE, MEMFLAG_PURE );
flags = fullflags->flags;
} else {
flags = MEMFLAG_MOVEABLE|MEMFLAG_PURE;
}
AddBitmapResource( name, flags, full_filename );
break;
case Y_FONT:
if (fullflags != NULL) {
SemCheckMemFlags( fullflags, 0,
MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE,
MEMFLAG_PURE );
flags = fullflags->flags;
} else {
flags = MEMFLAG_MOVEABLE|MEMFLAG_DISCARDABLE|MEMFLAG_PURE;
}
AddFontResources( name, flags, full_filename );
break;
default:
RcMemFree( name );
break;
}
RcMemFree( filename );
return;
HANDLE_ERROR:
ErrorHasOccured = TRUE;
RcMemFree( name );
RcMemFree( filename );
} /* SemAddSingleLineResource */
/*
* ReadBitmapInfoHeader-
* NB when an error occurs this func must return without altering errno
*/
static RcStatus ReadBitmapInfoHeader( BitmapInfoHeader * head, int handle )
/********************************************************************/
{
int numread;
numread = RcRead( handle, head, sizeof(BitmapInfoHeader) );
if( numread == sizeof( BitmapInfoHeader ) ) return( RS_OK );
if( numread == -1 ) return( RS_READ_ERROR );
return( RS_READ_INCMPLT );
}
static RcStatus readIcoCurFileDirHeader( IconCurDirHeader * head, int handle,
int *err_code )
/***********************************************************************/
{
int numread;
numread = RcRead( handle, head, sizeof(IconCurDirHeader) );
if( numread != sizeof( IconCurDirHeader ) ) {
*err_code = errno;
if( numread == -1 ) {
return( RS_READ_ERROR );
} else {
return( RS_READ_INCMPLT );
}
}
return( RS_OK );
} /* readIcoCurFileDirHeader */
static RcStatus readIcoFileDirEntry( IcoFileDirEntry * entry, int handle,
int *err_code )
/*******************************************************************/
{
int numread;
numread = RcRead( handle, entry, sizeof(IcoFileDirEntry) );
if( numread != sizeof(IcoFileDirEntry ) ) {
*err_code = errno;
if( numread == -1 ) {
return( RS_READ_ERROR );
} else {
return( RS_READ_INCMPLT );
}
}
return( RS_OK );
} /* readIcoFileDirEntry */
static RcStatus readIcoFileDir( int handle, FullIconDir *dir, int *err_code )
/***************************************************************************/
/* this funtion returns one of the above enum constants */
{
RcStatus error;
int currentry;
FullIconDirEntry * entry;
error = readIcoCurFileDirHeader( &(dir->Header), handle, err_code );
/* type 1 is a icon file */
if( error == RS_OK && dir->Header.Type != 1 ) {
return( RS_INVALID_RESOURCE );
}
for (currentry = 0; error == RS_OK && currentry < dir->Header.ResCount;
currentry++) {
entry = RcMemMalloc( sizeof(FullIconDirEntry) );
entry->Next = NULL;
entry->Prev = NULL;
entry->IsIcoFileEntry = TRUE;
error = readIcoFileDirEntry( &(entry->Entry.Ico), handle, err_code );
if( error != RS_OK ) {
RcMemFree( entry );
} else {
ResAddLLItemAtEnd( (void **) &(dir->Head), (void **)&(dir->Tail), entry );
}
}
return( error );
} /* readIcoFileDir */
static RcStatus copyOneIcon( const IcoFileDirEntry *entry, int handle,
void *buffer, int buffer_size, BitmapInfoHeader *dibhead,
int *err_code )
/**************************************************************************/
/* NOTE: this routine fills in dibhead as it copies the data */
{
RcStatus error;
long seekrc;
error = RS_OK;
seekrc = RcSeek( handle, entry->Offset, SEEK_SET );
if( seekrc == -1 ) {
error = RS_READ_ERROR;
*err_code = errno;
}
if( error == RS_OK ) {
error = ReadBitmapInfoHeader( dibhead, handle );
*err_code = errno;
}
if( error == RS_OK ) {
if( ResWriteBitmapInfoHeader( dibhead, CurrResFile.handle ) ) {
error = RS_WRITE_ERROR;
*err_code = LastWresErr();
}
}
if( error == RS_OK ) {
seekrc = RcTell( handle );
if( seekrc == -1 ) {
error = RS_READ_ERROR;
*err_code = errno;
} else {
error = CopyData( seekrc,
entry->Info.Length - sizeof(BitmapInfoHeader),
handle, buffer, buffer_size, err_code );
}
}
return( error );
} /* copyOneIcon */
#define BUFFER_SIZE 1024
static RcStatus copyIcons( FullIconDir * dir, int handle, ResMemFlags flags,
int *err_code )
/**********************************************************************/
{
RcStatus error;
char * buffer;
FullIconDirEntry * entry;
BitmapInfoHeader dibhead;
ResLocation loc;
error = RS_OK;
buffer = RcMemMalloc( BUFFER_SIZE );
for (entry = dir->Head; entry != NULL; entry = entry->Next) {
/* copy the icon */
loc.start = SemStartResource();
/* NOTE: the dibhead structure is filled in as a result of this call */
error = copyOneIcon( &(entry->Entry.Ico), handle, buffer, BUFFER_SIZE,
&(dibhead), err_code );
if( error != RS_OK ) break;
loc.len = SemEndResource( loc.start );
/* add the icon to the RES file directory */
SemAddResourceFree( WResIDFromNum( CurrResFile.NextCurOrIcon ),
WResIDFromNum( (long)RT_ICON ), flags, loc );
/* change the reference in the ICON directory */
entry->IsIcoFileEntry = FALSE;
entry->Entry.Res.IconID = CurrResFile.NextCurOrIcon;
entry->Entry.Res.Info.Planes = dibhead.Planes;
entry->Entry.Res.Info.BitCount = dibhead.BitCount;
CurrResFile.NextCurOrIcon += 1;
}
RcMemFree( buffer );
return( error );
} /* copyIcons */
static void FreeIconDir( FullIconDir * dir )
/******************************************/
{
FullIconDirEntry * currentry;
FullIconDirEntry * oldentry;
currentry = dir->Head;
while (currentry != NULL) {
oldentry = currentry;
currentry = currentry->Next;
RcMemFree( oldentry );
}
} /* FreeIconDir */
static int writeIconDir( FullIconDir * dir, WResID * name, ResMemFlags flags,
int *err_code )
/****************************************************************************/
{
int error;
FullIconDirEntry * entry;
ResLocation loc;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -