|
|
|
/*
|
|
|
|
* khexedit - Versatile hex editor
|
|
|
|
* Copyright (C) 1999 Espen Sand, espensa@online.no
|
|
|
|
*
|
|
|
|
* This program 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 2 of the License, or
|
|
|
|
* (at your option) any later version.
|
|
|
|
*
|
|
|
|
* This program 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.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program; if not, write to the Free Software
|
|
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
|
|
|
#include <ctype.h>
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <tqwidget.h>
|
|
|
|
#include "hexvalidator.h"
|
|
|
|
|
|
|
|
CHexValidator::CHexValidator( TQWidget *tqparent, EState state,
|
|
|
|
const char *name )
|
|
|
|
:TQValidator( TQT_TQOBJECT(tqparent), name )
|
|
|
|
{
|
|
|
|
setState( state );
|
|
|
|
}
|
|
|
|
|
|
|
|
CHexValidator::~CHexValidator( void )
|
|
|
|
{
|
|
|
|
}
|
|
|
|
|
|
|
|
TQValidator::State CHexValidator::validate( TQString &string, int &/*pos*/ ) const
|
|
|
|
{
|
|
|
|
if( mState == hexadecimal )
|
|
|
|
{
|
|
|
|
for( uint i=0; i < string.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = string[i].latin1();
|
|
|
|
if( isxdigit( val ) == 0 && isspace( val ) == 0 )
|
|
|
|
{
|
|
|
|
return( TQValidator::Invalid );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return( TQValidator::Valid );
|
|
|
|
}
|
|
|
|
if( mState == decimal )
|
|
|
|
{
|
|
|
|
for( uint i=0; i < string.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = string[i].latin1();
|
|
|
|
if( isdigit( val ) == 0 && isspace( val ) == 0 )
|
|
|
|
{
|
|
|
|
return( TQValidator::Invalid );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return( TQValidator::Valid );
|
|
|
|
}
|
|
|
|
else if( mState == octal )
|
|
|
|
{
|
|
|
|
for( uint i=0; i < string.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = string[i].latin1();
|
|
|
|
if( (isdigit( val ) == 0 || val == '8' || val == '9') &&
|
|
|
|
isspace( val ) == 0 )
|
|
|
|
{
|
|
|
|
return( TQValidator::Invalid );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return( TQValidator::Valid );
|
|
|
|
}
|
|
|
|
else if( mState == binary )
|
|
|
|
{
|
|
|
|
for( uint i=0; i < string.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = string[i].latin1();
|
|
|
|
if( val != '0' && val != '1' && isspace( val ) == 0 )
|
|
|
|
{
|
|
|
|
return( TQValidator::Invalid );
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return( TQValidator::Valid );
|
|
|
|
}
|
|
|
|
else if( mState == regularText )
|
|
|
|
{
|
|
|
|
return( TQValidator::Valid );
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return( TQValidator::Invalid );
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void CHexValidator::setState( EState state )
|
|
|
|
{
|
|
|
|
mState = state;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void CHexValidator::convert( TQByteArray &dest, const TQString &src )
|
|
|
|
{
|
|
|
|
uint value;
|
|
|
|
uint k=0;
|
|
|
|
|
|
|
|
if( mState == hexadecimal )
|
|
|
|
{
|
|
|
|
dest.resize(0);
|
|
|
|
|
|
|
|
char buf[3];
|
|
|
|
for( uint i=0; i < src.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = src[i].latin1();
|
|
|
|
if( isxdigit(val) )
|
|
|
|
{
|
|
|
|
buf[k++] = val;
|
|
|
|
if( k == 2 )
|
|
|
|
{
|
|
|
|
buf[k] = 0;
|
|
|
|
sscanf( buf, "%X", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
k = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if( k == 1 )
|
|
|
|
{
|
|
|
|
buf[1] = buf[0];
|
|
|
|
buf[0] = '0';
|
|
|
|
buf[2] = 0;
|
|
|
|
sscanf( buf, "%X", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
else if( mState == decimal )
|
|
|
|
{
|
|
|
|
dest.resize(0);
|
|
|
|
|
|
|
|
char buf[4];
|
|
|
|
for( uint i=0; i < src.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = src[i].latin1();
|
|
|
|
if( isdigit(val) )
|
|
|
|
{
|
|
|
|
buf[k++] = val;
|
|
|
|
if( k == 3 )
|
|
|
|
{
|
|
|
|
buf[k] = 0;
|
|
|
|
sscanf( buf, "%u", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
k = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if( k == 1 || k == 2 )
|
|
|
|
{
|
|
|
|
if( k == 1 )
|
|
|
|
{
|
|
|
|
buf[2] = buf[0];
|
|
|
|
buf[0] = buf[1] = '0';
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
buf[2] = buf[1];
|
|
|
|
buf[1] = buf[0];
|
|
|
|
buf[0] = '0';
|
|
|
|
}
|
|
|
|
buf[3] = 0;
|
|
|
|
sscanf( buf, "%u", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
else if( mState == octal )
|
|
|
|
{
|
|
|
|
dest.resize(0);
|
|
|
|
|
|
|
|
char buf[4];
|
|
|
|
for( uint i=0; i < src.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = src[i].latin1();
|
|
|
|
if( isdigit(val) )
|
|
|
|
{
|
|
|
|
buf[k++] = val;
|
|
|
|
if( k == 3 )
|
|
|
|
{
|
|
|
|
if( buf[0] > '3' ) { buf[0] = '3'; }
|
|
|
|
buf[k] = 0;
|
|
|
|
sscanf( buf, "%o", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
k = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if( k == 1 || k == 2 )
|
|
|
|
{
|
|
|
|
if( k == 1 )
|
|
|
|
{
|
|
|
|
buf[2] = buf[0];
|
|
|
|
buf[0] = buf[1] = '0';
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
buf[2] = buf[1];
|
|
|
|
buf[1] = buf[0];
|
|
|
|
buf[0] = '0';
|
|
|
|
}
|
|
|
|
buf[3] = 0;
|
|
|
|
sscanf( buf, "%o", &value );
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if( mState == binary )
|
|
|
|
{
|
|
|
|
dest.resize(0);
|
|
|
|
|
|
|
|
char buf[9];
|
|
|
|
for( uint i=0; i < src.length(); i++ )
|
|
|
|
{
|
|
|
|
int val = src[i].latin1();
|
|
|
|
if( isdigit(val) )
|
|
|
|
{
|
|
|
|
buf[k++] = val;
|
|
|
|
if( k == 8 )
|
|
|
|
{
|
|
|
|
value = 0;
|
|
|
|
for( uint j=0; j < 8; j++ )
|
|
|
|
{
|
|
|
|
value |= (buf[8-j-1] == '1') ? 1<<j : 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
k = 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if( k > 0 )
|
|
|
|
{
|
|
|
|
value = 0;
|
|
|
|
for( uint j=0; j < k; j++ )
|
|
|
|
{
|
|
|
|
value |= (buf[k-j-1] == '1') ? 1<<j : 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
dest.resize( dest.size()+1 );
|
|
|
|
dest[ dest.size()-1 ] = value;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else if( mState == regularText )
|
|
|
|
{
|
|
|
|
dest.resize(src.length());
|
|
|
|
for( uint i=0; i < src.length(); i++ )
|
|
|
|
{
|
|
|
|
dest[i] = src[i].latin1();
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
dest.resize(0);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
void CHexValidator::format( TQString &dest, const TQByteArray &src )
|
|
|
|
{
|
|
|
|
for( uint i=0; i<src.size(); ++i )
|
|
|
|
{
|
|
|
|
unsigned char srcCh = (unsigned char)src[i];
|
|
|
|
TQString formattedCh;
|
|
|
|
|
|
|
|
switch( mState )
|
|
|
|
{
|
|
|
|
case hexadecimal:
|
|
|
|
formattedCh = zeroExtend( TQString::number( srcCh, 16 ), 2 );
|
|
|
|
break;
|
|
|
|
case decimal:
|
|
|
|
formattedCh = zeroExtend( TQString::number( srcCh, 10), 3 );
|
|
|
|
break;
|
|
|
|
case octal:
|
|
|
|
formattedCh = zeroExtend( TQString::number( srcCh, 8), 3 );
|
|
|
|
break;
|
|
|
|
case binary:
|
|
|
|
formattedCh = zeroExtend( TQString::number( srcCh, 2), 8 );
|
|
|
|
break;
|
|
|
|
case regularText:
|
|
|
|
formattedCh = TQString( TQChar( srcCh ) );
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
dest += formattedCh + " ";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
TQString CHexValidator::zeroExtend( const TQString &src, unsigned destLen) const
|
|
|
|
{
|
|
|
|
if( src.length() >= destLen )
|
|
|
|
return src;
|
|
|
|
|
|
|
|
TQString zeroes;
|
|
|
|
zeroes.fill( '0', destLen - src.length() );
|
|
|
|
return zeroes + src;
|
|
|
|
}
|
|
|
|
#include "hexvalidator.moc"
|