| Store | Cart

Re: DBD for (Visual) DataFlex?

From: David H. Lynch Jr. <dhl...@1dla.com>
Tue, 15 Oct 2002 00:48:05 -0400
I am in the process of developing a PurePerl DBD driver for DataFlex files.

In the process I have deciphered the attached information regarding DatFlex
file formats.
I am fairly certain that DataFlex's data file format has not changed since
DF 3.0. That includes
all versions of Visual DataFlex.

While I consider myself to be a competent programmer, My knowledge of Perl
has some fairly
large gaps. I can accomplish what i need to and love it as a language, but
my solutions are not
nearly as elegant (or cryptic) as others. Anyway, I hope to be able to
release a pre-alpha readonly
version shortly. The driving force behind this is that I need it myself.
While my need is high my
requirements are not, so additional functionality (support for index files,
... may wait)

Reading through a number of drivers they appear to refer to information not
contained in the
DBD driver writers guide 11.2. I havenot found any other refernce available
for writing DBD
drivers. Is there further information available ?

Is there any somewhat standardized definition of what a DSN is ?
Most of the file based drivers I have read either treat it as a directory
containing the appropriate files,
or just an individual file. The DataFlex definition of a Database most
closely corresponds to an SQL table.
There is no direct equivalent of an SQL database, but DataFlex has a config
file that basically is a table
of available databases. Dataflex requires that to handle its approximate
equivalent of Joins but these are
hard wired and I see no need to support them. Further DF will search a path
for the "Databases" it is
looking for (so long as they are in the config file). My conception of a DSN
is a path where all found DF
Databases become Tables in the Database/DSN. Is there any reason to reject
that ?

Finally, am I correct in reading that the only subs in the module that
absolutely must directly manipulate
the file are:
        statement::open_table
        statement::seek
        statement::fetch_row
and   statement::push_row ?

Thank You.

"Jaap Voets" <jvo...@emea.att.com> wrote in message
news:DE57...@gbpormsx02.emea.att.com...
> I hope this is the right place to ask this question. If not please accept
my
> apologies.>> I've been looking around for a DBD module to fetch data from DataFlex
files.
> Personally I never heard about the product before someone handed me over> some very nice data  that was inside a DataFlex database. There are some> commercial products around that can interface with this data, but these
are
> way to expensive for the non-profit website I program for. The only thing
at
> moment I would like to do is read from the DataFlex files from within
perl.
>> Does anyone have experience with DataFlex, or maybe a file format> description? Some prototype code for this database that never left your
PC?
>> regards>> jaap voets>> ps. www.dataaccess.com is the company that produces dataflex.


	

		DATAFLEX 3.0 DATAFILE HEADER STRUCTURE

This description of the Dataflex 3.0+ file structure is loosely based on a 
2.3b file description I was able to find on the web done by:

By Peter M. Grillo
MAINSTREAM COMPUTER CONSULTING

In the course of developing a DBI driver for Datafle 3.x format .DAT files
I have had to update it to reflect the similar but different structure of a
DF 3.x format database. I have focused on deciphering the information that 
I needed for that purpose. So far the information I have deciphered has
been more than suffiicient to meet my needs. Hopefully it can be of use to 
others.


The DF 3.x .DAT file divides into two portions:

	A header containing information describing the contents of the file.
	A body starting with the NULL record with 1 record for each record 
	in the database.


The .HDR file that is created if header integrity is enabled is virtually 
identical to the header portion of the database up through record 0.
However it may have slightly different checksum values and some record
count fields are sometimes slightly behind.


All values in the header are stored in LSB-MSB order.

The Header has several portions.


	The Primary header.

		This has feilds describing overal attributes and options
of the .DAT file as follows:

offset from start of file (hex) Description

0x0  	DWORD 			Highest Record Number (ever) 
0x4  	DWORD   		Has something to do with reuse of deleted space
				0 if deleted space is not re-used
				undeciphered value - possibly first available record # otherwise.

0x8  	DWORD			Records used 
0xc  	DWORD			Maximum records (set in DFILE parameters)
0x10   	DWORD	 		? header integrity 
				0 if header integrity disabled
				? Checksum if enabled
0x14  	DWORD   		? Checksum
				There apear to be 4 of these at
					0x14
					0x18
					0x38
					0x50
				Originally I thought these were date/time 
				stamps, but now I am suspicious that they
				are some type of checksum. Anyway they change 
				pretty much any time that you make a change to 
				a file with DFFILE.
0x18	DWORD			? Checksum 
0x1c  	BYTE	30		I beleive this is the file format version.
	BYTE	30		Bytes 0x1c and 0x1d appear to always be 0x1e or 30 decimal
		 
0x1e	BYTE	0
0x1f	BYTE			Compression 0=none 1=fast 2=standard 3=
0x20  	DWORD   		? First available record
				0 if deleted space is re-used 
0x28	DWORD			0, undeciphered if Compresion
0x30	DWORD			0, undeciphered if standard compression
0x38	DWORD			? Checksum
0x3c	DWORD			? always 0 	
0x40	BYTE			related to header integrity.  0= disabled undeciphered if enabled
0x41	BYTE			File Locking 1=True 0=false
0x4a	WORD			0=Reuse deleted space -1= do not.  -1= Compression
0x4c	WORD			? Checksum changes more frequently than the DWORD checksums
0x50	DWORD			? Checksum 
0x98	WORD			Records until remainder block 
				Basically records/512 byte block or
				1 for anything that has no remainder blocks.
0x9a	WORD			Record Length 	
0xa4	BYTE			Reuse Deleted records 1=True 0=false
0xa5	BYTE			Fields/Record 
0xa8	BYTE			File Locking 1=true 0=false
0xa9	BYTE			? always 1
0xad	BYTE			? always 1	
0xae	BYTE			? 
		
0xb0	Index Table

	16 Entries of 18 Bytes each as follows:

	BYTE			Number of fields in index + 0x80 if the index is a Batch index
    16  BYTES			Field numbers for each segment
    	BYTE			Flag byte 0x1 = Descending/Ascending 0x2 = Uppercase

	
0x2d0	Datbase Name
    16 Bytes			File root name Null filled

0x2e0 	Field Definition table 

	256 entries of 8 bytes
	
	WORD			Offset from start of record
	BYTE			High Nibble = Main Index Number
				Low Nibble = Decimal points/2
	BYTE			Field Length (Bytes)
    					Bytes/ASCII
					Bytes/16 for TEXT/Binary

	BYTE			Field Type
					0 = ASCII
					1 = Numeric
					2 = Date
					3 = Overlap
					5 = Text 
					6 = Binary 

   	BYTE			Relates to file #
	WORD			Relates to Field #

	
0x0c00	Record # 0 Null filled

	Follwed by records in database in record number order blocked to 512 byte blocks
	with block fill as required.


	I have not needed to dicipher any of the compression schemes used. 
	When data is uncompressed fields occur in the record in the order they are defined, 
	though the field table format would allow them to be in a different order.

	ASCII values are stored as ASCII data 1 character/byte with fields blank filled.
	NUMBER values are stored as BCD encoded numbers with the decimal point located by the field
	definition.
	DATE values are stored as binary day numbers in 3 bytes, LSB first.
	Size values for ASCII, NUMBER and DATE are in bytes
	
	TEXT and BINARY values are stored 1 BYTE/BYTE 
	Size values are in 16 byte multiples.
	
	
Index File Format

	The indexes are in 1024 byte blocks
	each block starts with 4 bytes
	The 3rd byte is the count of records in the block.
	The blocks are 0 filled
	The  index records start at offset 4 in the block
	The index is basically the data values from the index fields stored in order 
		of the index keys:
		Ascii Values are converted to their collating sequence numbers first
		In the american coalating sequence 
		A=204 and the order of characters is AaBb...
		Non-ascii values are as they are stored in the DB
	There is a 3 byte field pointing to the record number in the file at the end of the index record

	I beleive the index records are in order from the physical start of the file through the end and 
	the blocking and null filling of the index bocks is to make it easier to insert index records.
	Most of the Indexes that I have dumped seem to have room for several additional records at the 
	end of each block.

	There is a possible use for the index files beyond that of progressing through the file in a 
	specific order. It should be possible to reconstruct the data for those fields of a database
	that are contained in the index by extracting the data from the indexes if they are available.
	In many instances many or all fields of a database participate in the index. Aside from converting
	the ASCII values from their collalating equivalents, this should actually be fairly simple and 
	there are certainly instances in the past where I wish I had that capability.

I have no particular need for Filelist.cfg for my purposes but it seems to remain as described in 
the 2.3b format file by Peter M. Grillo Listed below except that it can be extended to more records
for more files:

	Filelist.cfg is a collection of 128 byte records. 1 per file in order by DF File number.
	Record 0 contains the Root File name Filelist.cfg and is otherwise null filled.
	Record 1 corresponds to DF file # 1

Hex      		Description

0x0 	BYTE 		File Root Name	(Null Filled)
0x29 	BYTE		File Description (Null Filled)
0x4A 	BYTE		Dataflex File Name (Null Filled)

COPYRIGHT


       David H. Lynch Jr.
       <dhl...@1dla.com>

   Copyright (C) 2002 by David H. Lynch Jr.

   All rights reserved.

	Aside from Peter Crillo's DF 2.3b File format description, my own poking around,
	and the insights gained from 20 years fo DF programing, I have not used any 
        DataAccess information or resources. Therefore this is an original work.
	I beleive DataAccess considers the DataFlex File formats proprietary. 
	Any use you make of this information is at your own risk.

	If you are able to advance the knowledge contained in this file without
	making use of information sources that would violate the terms and conditions of
	licenses or agreements with DataAccess and you are willing to forward that 
	information to (dhl...@1dla.com> I will incorporate it with credit in any future 
	releases there may be of this file.

	Further the purpose of gathering this information was the development of 
	a perl DBD driver for Dataflex. I am currently engaged in that effort and 
	hope to have a read only version that does not support indexes shortly.
	I expect to post notice of that with the Perl DBD developers and that web 
	site will reflect the current status. In the event you might wish to 
	assist with the development feel free to contact me. I can use all the 
	help I can get. I am doing this primarily because I need it and no one 
	else has done it.
	
   You may distribute this under the terms of the GNU General Public License.

VERSION
    This document refers to version 0.01 of df30.txt, released Oct 10, 2002.

AUTHOR
    David H. Lynch Jr:. (dhl...@1dla.com)
Recent Messages in this Thread
David H. Lynch Jr. Oct 15, 2002 04:48 am