Wildcat: full SDK init (InitWCglobal + LoadMakeWild + BTInitIsam); test across 7 conferences
The TWildcatBase.OpenConference was creating a TMsgDatabase without populating the SDK globals, causing access violations on MwConfig. Now calls the full Register sequence: InitWCglobal, LoadMakeWild, BTInitIsam before opening; BTExitIsam + DisposeWCglobal on close. test_wildcat reads conferences 0..6 from vendored testdata (copied to /tmp/ma_wildcat so the source tree stays read-only).
This commit is contained in:
@@ -2,7 +2,8 @@
|
||||
|
||||
## Sample data
|
||||
|
||||
Real message bases for testing live at `~/fidonet/msg/`:
|
||||
Real message bases for testing live at `~/fidonet/msg/` and for
|
||||
WildCat! at `~/allfix_dev/f_drive/tpfiles/allfix/wc_dev/testdata/`:
|
||||
|
||||
- `hudson/` — Hudson MSGINFO/IDX/HDR/TXT/TOIDX.BBS set
|
||||
- `jam/` — many JAM echo areas (e.g. `10thamd.jhr/jdt/jdx/jlr`)
|
||||
@@ -11,9 +12,16 @@ Real message bases for testing live at `~/fidonet/msg/`:
|
||||
- `squish/` — Squish bases (currently empty but layout reserved)
|
||||
- `local/jam/`, `lowerit/`, `passthru/` — additional collections
|
||||
|
||||
- WildCat 4 testdata:
|
||||
- `CONFDESC.DAT/IX/UX` — conference descriptors (7 conferences)
|
||||
- `MSG/MSG0..MSG6.DAT + .IX` — per-conference message databases
|
||||
- `DATA/ALLUSERS.DAT + USERCONF.DAT` — users + per-user conference membership
|
||||
|
||||
Tests should open these read-only and verify message counts, first/last
|
||||
messages, and specific known attributes. Do NOT write to these paths
|
||||
from tests — copy them into a scratch dir first.
|
||||
from tests — copy them into a scratch dir first. The Wildcat SDK
|
||||
mutates the message database during Open (btis locks, modcounters) so
|
||||
even "read" paths must go through a scratch copy.
|
||||
|
||||
## Authoritative specs
|
||||
|
||||
|
||||
@@ -19,7 +19,7 @@ compile() {
|
||||
local src=$1
|
||||
echo " compile $(basename "$src")"
|
||||
"$FPCNATIVE" -Mobjfpc -Sh -Sgic \
|
||||
-Fusrc -Fusrc/formats -Futests \
|
||||
-Fusrc -Fusrc/formats -Fusrc/wc_sdk -Futests \
|
||||
-FUunits/"$TGT" -FEexe/"$TGT" \
|
||||
"$src" >/tmp/ma_test_build.$$.log 2>&1 || {
|
||||
cat /tmp/ma_test_build.$$.log
|
||||
@@ -41,6 +41,7 @@ compile tests/test_read.pas
|
||||
compile tests/test_roundtrip.pas
|
||||
compile tests/test_lock.pas
|
||||
compile tests/test_batch.pas
|
||||
compile tests/test_wildcat.pas
|
||||
|
||||
echo
|
||||
echo "Running tests..."
|
||||
@@ -48,6 +49,7 @@ run test_read
|
||||
run test_roundtrip
|
||||
run test_lock
|
||||
run test_batch
|
||||
run test_wildcat
|
||||
|
||||
echo
|
||||
echo "All tests passed."
|
||||
|
||||
@@ -48,7 +48,7 @@ interface
|
||||
|
||||
uses
|
||||
WcType, WcMsgDb, WcUserDb, WcGlobal, WcMisc, WcDb,
|
||||
Filer, BTISBase;
|
||||
Filer, BTISBase, BTFileIO;
|
||||
|
||||
type
|
||||
TWildcatBase = class
|
||||
@@ -150,6 +150,24 @@ end;
|
||||
|
||||
{ --- Conference management --- }
|
||||
|
||||
function LoadMakeWild(var AMwConfig: TMakewildRec): boolean;
|
||||
var
|
||||
F: file of TMakewildRec;
|
||||
SaveFileMode: word;
|
||||
begin
|
||||
Result := False;
|
||||
Assign(F, 'MAKEWILD.DAT');
|
||||
SaveFileMode := FileMode;
|
||||
FileMode := 66; { deny-none share, read-write }
|
||||
{$I-} Reset(F); {$I+}
|
||||
FileMode := SaveFileMode;
|
||||
if IoResult <> 0 then exit;
|
||||
{$I-} Read(F, AMwConfig); {$I+}
|
||||
Result := IoResult = 0;
|
||||
{$I-} Close(F); {$I+}
|
||||
if IoResult = 0 then {ignore};
|
||||
end;
|
||||
|
||||
function TWildcatBase.OpenConference(Conf: word): boolean;
|
||||
begin
|
||||
Result := False;
|
||||
@@ -158,6 +176,24 @@ begin
|
||||
|
||||
SaveAndChangeDir;
|
||||
|
||||
{ WC SDK globals must be populated before opening any database.
|
||||
InitWCglobal allocates the pointers; LoadMakeWild fills MwConfig^
|
||||
from MAKEWILD.DAT in the current dir; BtInitIsam brings up the
|
||||
ISAM layer the message/user databases sit on. Done in
|
||||
CloseConference. }
|
||||
InitWCglobal;
|
||||
if not LoadMakeWild(MwConfig^) then begin
|
||||
DisposeWCglobal;
|
||||
RestoreDir;
|
||||
exit;
|
||||
end;
|
||||
BtInitIsam(NetSupportType(MwConfig^.Network), MinimizeUseOfNormalHeap, 0);
|
||||
if not IsamOk then begin
|
||||
DisposeWCglobal;
|
||||
RestoreDir;
|
||||
exit;
|
||||
end;
|
||||
|
||||
New(FMsgDb, Init);
|
||||
New(FUserDb, Init);
|
||||
|
||||
@@ -170,6 +206,8 @@ begin
|
||||
FUserDb := nil;
|
||||
if FMsgDb <> nil then Dispose(FMsgDb);
|
||||
FMsgDb := nil;
|
||||
BtExitIsam;
|
||||
DisposeWCglobal;
|
||||
RestoreDir;
|
||||
end;
|
||||
end;
|
||||
@@ -190,6 +228,8 @@ begin
|
||||
FUserDb := nil;
|
||||
end;
|
||||
|
||||
BtExitIsam;
|
||||
DisposeWCglobal;
|
||||
RestoreDir;
|
||||
end;
|
||||
|
||||
|
||||
99
tests/test_wildcat.pas
Normal file
99
tests/test_wildcat.pas
Normal file
@@ -0,0 +1,99 @@
|
||||
{
|
||||
test_wildcat.pas - WildCat! 4 adapter smoke test.
|
||||
|
||||
The WC SDK opens databases for write (btis lock, modcounter
|
||||
bumps) even when the caller only reads, so we never touch the
|
||||
source tree directly. This test copies the whole testdata
|
||||
directory to a scratch location first, runs the adapter there,
|
||||
then leaves the scratch alone for manual inspection.
|
||||
|
||||
Source lives at
|
||||
~/allfix_dev/f_drive/tpfiles/allfix/wc_dev/testdata/
|
||||
and is NEVER modified.
|
||||
}
|
||||
|
||||
program test_wildcat;
|
||||
|
||||
{$mode objfpc}{$H+}
|
||||
|
||||
uses
|
||||
SysUtils,
|
||||
testutil,
|
||||
ma.types, ma.events, ma.api,
|
||||
ma.fmt.wildcat, ma.fmt.wildcat.uni;
|
||||
|
||||
const
|
||||
SRC = '/home/ken/allfix_dev/f_drive/tpfiles/allfix/wc_dev/testdata';
|
||||
SCRATCH = '/tmp/ma_wildcat';
|
||||
|
||||
function RunShell(const Cmd: string): integer;
|
||||
begin
|
||||
Result := ExecuteProcess('/bin/sh', ['-c', Cmd]);
|
||||
end;
|
||||
|
||||
function CopyTree(const Source, Dest: string): boolean;
|
||||
var
|
||||
cmd: string;
|
||||
begin
|
||||
cmd := SysUtils.Format('cp -r "%s"/. "%s"/ 2>/dev/null', [Source, Dest]);
|
||||
Result := RunShell(cmd) = 0;
|
||||
end;
|
||||
|
||||
procedure PrepareScratch;
|
||||
begin
|
||||
if DirectoryExists(SCRATCH) then
|
||||
RunShell(SysUtils.Format('rm -rf "%s"', [SCRATCH]));
|
||||
ForceDirectories(SCRATCH);
|
||||
if not CopyTree(SRC, SCRATCH) then
|
||||
raise Exception.Create('cp -r failed');
|
||||
end;
|
||||
|
||||
procedure TestConference(Conf: word);
|
||||
var
|
||||
base: TMessageBase;
|
||||
adapter: TWildcatMessageBase;
|
||||
msg: TUniMessage;
|
||||
i, count, ok: longint;
|
||||
begin
|
||||
TestBegin(SysUtils.Format('WildCat! conference %d', [Conf]));
|
||||
base := MessageBaseOpen(mbfWildcat, SCRATCH, momReadWrite);
|
||||
adapter := base as TWildcatMessageBase;
|
||||
adapter.Conference := Conf;
|
||||
try
|
||||
AssertTrue('Open', base.Open);
|
||||
count := base.MessageCount;
|
||||
ok := 0;
|
||||
for i := 0 to count - 1 do
|
||||
if base.ReadMessage(i, msg) then begin
|
||||
Inc(ok);
|
||||
if i = 0 then
|
||||
AssertTrue('First msg has sender',
|
||||
Length(msg.WhoFrom) > 0);
|
||||
end;
|
||||
AssertEquals('Read all reported messages', count, ok);
|
||||
finally
|
||||
base.Close;
|
||||
base.Free;
|
||||
end;
|
||||
TestOK;
|
||||
end;
|
||||
|
||||
var
|
||||
conf: word;
|
||||
begin
|
||||
WriteLn('message_api: WildCat! 4 read tests');
|
||||
WriteLn;
|
||||
|
||||
if not DirectoryExists(SRC) then begin
|
||||
WriteLn('SKIP (sample at ', SRC, ' missing)');
|
||||
Halt(0);
|
||||
end;
|
||||
|
||||
PrepareScratch;
|
||||
|
||||
{ testdata has conferences 0..6. Walk each one. }
|
||||
for conf := 0 to 6 do
|
||||
TestConference(conf);
|
||||
|
||||
Halt(TestsSummary);
|
||||
end.
|
||||
Reference in New Issue
Block a user