home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
High Voltage Shareware
/
high1.zip
/
high1
/
DIR13
/
INIFIL.ZIP
/
INIFILE.CPP
< prev
next >
Wrap
C/C++ Source or Header
|
1993-10-13
|
11KB
|
431 lines
/*
Copyright (c) 1993, George Byrkit
Software Professionals Limited
1809 Saxon Street
Ann Arbor, MI 48103
(313)-663-1009
ALL RIGHTS RESERVED
THIS FILE MAY BE INCLUDED ROYALTY-FREE in any program as long as the
above copyright notice also appears in the text of the program executable.
I hereby certify that I did NOT examine the internals of the equivalent
Windows (reg TM of MicroSoft) functions in order to create these
approximately functionally equivalent routines.
Differences are:
I don't look for a windows installation directory. If you use the
non-private functions, the file 'win.ini' is looked for in the CURRENT
DIRECTORY
filename: inifile.cpp
purpose: emulate windows API functions to access the ini files
instructions for building:
compile:
link:
other:
change log:
When Version Who Why
01-jan-93 1.0 ghb created
*/
/*
PRAGMAS
*/
/*
INCLUDE FILES
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include "inifile.h"
/*
LOCAL DEFINES AND MACROS
*/
/*
LOCAL STRUCTURES AND TYPEDEFS
*/
/*
FORWARD REFERENCES TO FUNCTIONS DEFINED IN THIS SOURCE FILE
*/
/*
EXTERN FUNCTION AND DATA REFERENCES
*/
/*
LOCAL DATA (MAY BE GLOBAL OR STATIC)
*/
/*
this string MUST be part of the executable file for the functions in
this file to be used in a non-infringing way
*/
static char *pCWN = "inifile code is Copyright (c) 1993, George Byrkit\n"
"Software Professionals Limited\n"
"1809 Saxon Street\n"
"Ann Arbor, MI 48103\n"
"(313)-663-1009\n"
"ALL RIGHTS RESERVED\n";
/*
Note that appname and keyname are treated case-insensitively.
*/
/*
returns a pointer to the line that contains the desired string
open for write opens a file from the beginning
*/
/*
basic finding function for reads.
see ScanForCopy for use with writes
*/
int ScanFor ( LPCSTR lpAppName, LPCSTR lpKeyName,
LPSTR lpReturnedString, int nSize,
FILE *pIniFile )
{
int appLen = strlen ( lpAppName );
int keyLen = strlen ( lpKeyName );
char *rc;
// find application name, if present
do {
rc = fgets ( lpReturnedString, nSize, pIniFile );
// check for error, possibly EOF.
if ( rc != lpReturnedString ) {
// didn't find the application. Return not found
return 0;
}
} while ( lpReturnedString[0] != '['
|| strnicmp ( lpAppName, &lpReturnedString[1], appLen )
|| lpReturnedString[1+appLen] != ']' );
// OK, we found the application section. Now look for the keyword
do {
rc = fgets ( lpReturnedString, nSize, pIniFile );
// check for error, possibly EOF.
if ( rc != lpReturnedString ) {
// didn't find the application. Return not found
return 0;
}
// at the end of an application. Obviously we didn't find the keyword
if ( lpReturnedString[0] == '[' ) {
// didn't find the keyword. Return not found
return 0;
}
} while ( strnicmp ( lpKeyName, lpReturnedString, keyLen )
|| lpReturnedString[keyLen] != '=' );
// OK, we found it, and it's in the current buffer. Return success.
// Success is the nonzero index into the return string of where
// the result (after the equal sign) is located
return keyLen+1;
}
/*
basic finding function for writes.
see ScanFor for use with reads
*/
InsertSection ( LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpValue, FILE *pFile )
{
return fprintf ( pFile, "[%s]\n%s=%s\n", lpAppName, lpKeyName, lpValue );
}
InsertKey ( LPCSTR lpKeyName, LPCSTR lpValue, FILE *pFile )
{
return fprintf ( pFile, "%s=%s\n", lpKeyName, lpValue );
}
/*
return of zero means no more copy to do.
*/
int ScanForCopyInsert ( LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpValue,
FILE *pIniFile, FILE *pIniFileCopy )
{
int appLen = strlen ( lpAppName );
int keyLen = strlen ( lpKeyName );
char lpReturnedString [256];
char *rc;
// find application name, if present
do {
rc = fgets ( lpReturnedString, 256, pIniFile );
// check for error, possibly EOF.
if ( rc != lpReturnedString ) {
// didn't find the application. Return not found
InsertSection ( lpAppName, lpKeyName, lpValue, pIniFileCopy );
return 0;
}
// copy to output
fputs ( lpReturnedString, pIniFileCopy );
} while ( lpReturnedString[0] != '['
|| strnicmp ( lpAppName, &lpReturnedString[1], appLen )
|| lpReturnedString[1+appLen] != ']' );
// OK, we found the application section. Now look for the keyword
do {
rc = fgets ( lpReturnedString, 256, pIniFile );
// check for error, possibly EOF.
if ( rc != lpReturnedString ) {
// didn't find the application. Return not found
InsertKey ( lpKeyName, lpValue, pIniFileCopy );
return 1;
}
// at the end of an application. Obviously we didn't find the keyword
if ( lpReturnedString[0] == '[' ) {
InsertKey ( lpKeyName, lpValue, pIniFileCopy );
// copy the line in the buffer, that we just read, that starts
// a new section
fputs ( lpReturnedString, pIniFileCopy );
// didn't find the keyword. Return not found
return 1;
}
if ( !strnicmp ( lpKeyName, lpReturnedString, keyLen )
&& lpReturnedString[keyLen] == '=' ) {
// this is the place
break;
}
} while ( fputs ( lpReturnedString, pIniFileCopy ) != EOF );
// OK, we found it, and it's in the current buffer. Replace what's after
// the equal sign and up to any comment, with what's in the string we got
// here to write in
rc = strchr ( &lpReturnedString[keyLen+1], ';' );
// we got a trailing comment. Now back up over whitespace
if ( rc ) {
while ( isspace(*(rc-1)) ) {
rc--; // back up
}
// note that rc usually includes a newline character
if ( !strchr ( rc, '\n' ) ) {
// must provide a newline char, one wasn't there
fprintf ( pIniFileCopy, "%s=%s%s\n", lpKeyName, lpValue, rc );
}
else {
fprintf ( pIniFileCopy, "%s=%s%s", lpKeyName, lpValue, rc );
}
}
else {
fprintf ( pIniFileCopy, "%s=%s\n", lpKeyName, lpValue );
}
// indicate probably more to copy
return 1;
}
UINT WINAPI GetPrivateProfileInt(LPCSTR lpAppName, LPCSTR lpKeyName,
int nDefault,
LPCSTR lpFileName)
{
char returnedString[256];
UINT rc;
FILE *pIniFile = fopen ( lpFileName, "rt" );
if ( !pIniFile ) {
return nDefault;
}
rc = ScanFor ( lpAppName, lpKeyName, returnedString, 256, pIniFile );
if ( !rc ) {
return nDefault;
}
// get integer value
return (UINT) atol ( &returnedString[ rc ] );
}
int WINAPI GetPrivateProfileString(LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpDefault, LPSTR lpReturnedString, int nSize,
LPCSTR lpFileName)
{
char returnedString[256];
int rc;
int i;
int len;
char *p;
FILE *pIniFile = fopen ( lpFileName, "rt" );
if ( !pIniFile ) {
strcpy ( lpReturnedString, lpDefault );
return strlen ( lpDefault );
}
rc = ScanFor ( lpAppName, lpKeyName, returnedString, 256, pIniFile );
if ( !rc ) {
strcpy ( lpReturnedString, lpDefault );
return strlen ( lpDefault );
}
// get string. Copy out and back, to get rid of leading line info
strcpy ( returnedString, &returnedString[ rc ] );
// look for a double quote
if ( returnedString[0] == '\"' ) {
// find terminating quote
p = strchr ( &returnedString[1], '\"' );
p++;
*p = '\0'; // string is terminated after end quote
}
else if ( NULL != ( p = strchr ( returnedString, ';' ) ) ) {
// found a comment char
// terminate string there. Trailing whitespace trim will still work.
*p = '\0';
}
// trim off trailing whitespace
len = strlen ( returnedString );
for ( i = len-1; i > 0; i-- ) {
if ( isspace(returnedString[i]) ) {
returnedString[i] = '\0'; // trim it
}
else {
break;
}
}
strncpy ( lpReturnedString, returnedString, nSize - 1 );
lpReturnedString[nSize] = '\0'; // force null termination
return strlen ( lpReturnedString );
}
BOOL WINAPI WritePrivateProfileString(LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpValue,
LPCSTR lpFileName)
{
char tmpFileName[256];
char tmpFileName2[256];
char buffer[256];
int rc;
FILE *pIniFileCopy;
FILE *pIniFile = fopen ( lpFileName, "rt" );
// if it doesn't exist, create it and insert this section
if ( !pIniFile ) {
pIniFile = fopen ( lpFileName, "wt" );
if ( !pIniFile ) {
return 0; // failure
}
InsertSection ( lpAppName, lpKeyName, lpValue, pIniFile );
fclose ( pIniFile );
return 0;
}
// get a temporary file name that is unique
strcpy ( tmpFileName, lpFileName );
tmpFileName[strlen ( tmpFileName )-1] = '$'; // turn last char into $
pIniFileCopy = fopen ( tmpFileName, "wt" );
// if can't open a temporary file, fail
if ( !pIniFileCopy ) {
rc = errno;
fclose ( pIniFile );
return 0;
}
rc = ScanForCopyInsert ( lpAppName, lpKeyName, lpValue,
pIniFile, pIniFileCopy );
if ( rc ) {
while ( !feof ( pIniFile ) ) {
if ( buffer != fgets ( buffer, sizeof ( buffer ) -1, pIniFile ) ) {
if ( !feof ( pIniFile ) ) {
rc = errno;
fclose ( pIniFile );
fclose ( pIniFileCopy );
remove ( tmpFileName );
return 0;
}
else {
// it is end of file. All is copied. Swap files
break;
}
}
// while writing to the copy file, if an error is encountered
if ( fputs ( buffer, pIniFileCopy ) == EOF ) {
// error while writing
rc = errno;
fclose ( pIniFile );
fclose ( pIniFileCopy );
remove ( tmpFileName );
return 0;
}
} // end while not eof
}
// close the files
fclose ( pIniFile );
fclose ( pIniFileCopy );
// form the name of what to rename the current file to.
strcpy ( tmpFileName2, lpFileName );
tmpFileName2[strlen ( tmpFileName )-1] = '$'; // turn last char into $
tmpFileName2[strlen ( tmpFileName )-2] = '$'; // also nextlast char into $
rc = rename ( lpFileName, tmpFileName2 );
if ( rc ) {
// error on rename. can't do it. bail out
rc = errno;
remove ( tmpFileName );
return 0;
}
rc = rename ( tmpFileName, lpFileName );
if ( rc ) {
// error on rename. can't do it. bail out
rc = errno;
// rename back original file. Pray for no error!
rename ( tmpFileName2, lpFileName );
remove ( tmpFileName ); // delete temp file
return 0;
}
// all went OK. Now just delete the temp file that is the original file
remove ( tmpFileName2 ); // delete temp file that is original file
return 1;
}
UINT WINAPI GetProfileInt(LPCSTR lpAppName, LPCSTR lpKeyName,
int nDefault)
{
return GetPrivateProfileInt (lpAppName, lpKeyName, nDefault, "win.ini" );
}
int WINAPI GetProfileString(LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpDefault, LPSTR lpReturnedString, int nSize)
{
return GetPrivateProfileString (lpAppName, lpKeyName, lpDefault,
lpReturnedString, nSize, "win.ini" );
}
BOOL WINAPI WriteProfileString(LPCSTR lpAppName, LPCSTR lpKeyName,
LPCSTR lpValue)
{
return WritePrivateProfileString (lpAppName, lpKeyName, lpValue, "win.ini");
}
#ifdef TEST
main ()
{
char rv[256];
GetPrivateProfileString ( "myapp2", "key2", "none", rv, 256, "myapp.ini" );
printf ("Value of key %s in section %s is %s\n", "key2", "myapp2", rv );
}
#endif