[Okta Webinar] Learn how to a build a cloud-first strategyRegister Now

x
  • Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 165
  • Last Modified:

How to detect a not installed system library?

I am using netbios 3.0 to find out the MAC-address. It is using the function 'Netbios' in the system dll 'netbios32.dll'. Now, my boss is afraid it will crash when the computer has no network installed (no netbios32.dll).

To simulate the situation where there's no such library, I changed the name in 'netbiosx.dll' and everything compiled fine. But Delphi says dll not found even before it started the application. try except didn't help.

Question:

How to declare a function and find out at run time this function doesn't exist?
0
dnoelpp
Asked:
dnoelpp
1 Solution
 
dnoelppAuthor Commented:
Sorry, it should be 'netapi32.dll', not 'netbios.dll'.

And secondly, does someone of the experts know about the availability of the netbios on Windows machines and other machines (maybe on Linux)?
0
 
dnoelppAuthor Commented:
With "availability" I mean, under which circumstances you can expect to find this dll? Under which circumstances not?
0
 
geobulCommented:
Hi,
The answer is: dynamic loading of the dll:

type
 TDLLFunction=function(a:integer; b: PChar): integer; stdcall;

var
 DLLFunction: TDLLFunction;
 Handle:THandle;
begin
 // load the library
 Handle:=LoadLibrary('test.dll');
 // check if it is loaded
 if Handle<>0 then begin
   try
    // get the address of the function
    @DLLFunction := GetProcAddress(Handle, 'DLLFunction');
   // now call the function
   DLLFunction(10, PChar('Hello'));
  finally
   // unload the library
   FreeLibary(Handle);
  end;
 end else begin
   // library not found
   ShowMessage('test.dll not found!');
 end;
end;

Regards, Geo
0
Independent Software Vendors: We Want Your Opinion

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
CesarioCommented:
Hello dnoelpp,

I use this function to check if a DLL is installed :


Function DllOnSystem ( DllName:String):Boolean;
VAR
  Ret : Integer;
  good : Boolean;
Begin
  ret := LoadLibrary ( pChar(DllName));
  IF Ret>0 FreeLibrary ( ret );
  Result := Ret>0;
End;


Good Luck

Cesario
   
0
 
MathiasCommented:
Listening...
0
 
dnoelppAuthor Commented:
Thanks, but something is still unclear. The NetBios function is a function taking a pointer to a record (type PNCB) and returning a character. How do I call such a function dynamically?

And, does someone know about the availability of netapi32.dll? Especially can it happen that it is not present and under which circumstances?
0
 
dnoelppAuthor Commented:
Okay, now I found it. About the availability of netapi32.dll I will post another question (perhaps in the networking topic).

This is my working solution (pasted together out of Cesario's and geobul's answers), thanks a lot! It will return a question mark if either no NIC or no netapi32.dll is installed.

*** ***

uses
 NB30;

type
  TNetBiosFunction = function(P: PNCB): Char; stdcall;

const
  NONETAPI32 = $ac;


// Invoke the NetBios function of the netapi32.dll
// dynamically. If netapi32.dll is not installed,
// return the character value of NONETAPI.
function NetBios(P: PNCB): Char;
var
  NetBiosFunction: TNetBiosFunction;
  Handle: THandle;
begin
  Handle := LoadLibrary('netapi32.dll');
  if Handle <> 0 then begin
    try
      @NetBiosFunction := GetProcAddress(Handle, 'Netbios');
      Result := NetBiosFunction(P);
    finally
      FreeLibrary(Handle);
    end;
  end else begin
    Result := Char(NONETAPI32);
  end;
end;

function GetAdapterInfo(Lana: Char): String;
var
 Adapter: TAdapterStatus;
 NCB: TNCB;
begin
 FillChar(NCB, SizeOf(NCB), 0);
 NCB.ncb_command := Char(NCBRESET);
 NCB.ncb_lana_num := Lana;
 if Netbios(@NCB) <> Char(NRC_GOODRET) then
 begin
   Result := '?';
   Exit;
 end;

 FillChar(NCB, SizeOf(NCB), 0);
 NCB.ncb_command := Char(NCBASTAT);
 NCB.ncb_lana_num := Lana;
 NCB.ncb_callname := '*';

 FillChar(Adapter, SizeOf(Adapter), 0);
 NCB.ncb_buffer := @Adapter;
 NCB.ncb_length := SizeOf(Adapter);
 if Netbios(@NCB) <> Char(NRC_GOODRET) then
 begin
   Result := '?';
   Exit;
 end;
 Result :=
   IntToHex(Byte(Adapter.adapter_address[0]), 2) + '-' +
   IntToHex(Byte(Adapter.adapter_address[1]), 2) + '-' +
   IntToHex(Byte(Adapter.adapter_address[2]), 2) + '-' +
   IntToHex(Byte(Adapter.adapter_address[3]), 2) + '-' +
   IntToHex(Byte(Adapter.adapter_address[4]), 2) + '-' +
   IntToHex(Byte(Adapter.adapter_address[5]), 2);
end;

function GetMACAddress: string;
var
 AdapterList: TLanaEnum;
 NCB: TNCB;
begin
 FillChar(NCB, SizeOf(NCB), 0);
 NCB.ncb_command := Char(NCBENUM);
 NCB.ncb_buffer := @AdapterList;
 NCB.ncb_length := SizeOf(AdapterList);
 Netbios(@NCB);
 if Byte(AdapterList.length) > 0 then
   Result := GetAdapterInfo(AdapterList.lana[0])
 else
   Result := '?';
end;
0
 
dnoelppAuthor Commented:
0
 
geobulCommented:
Hi,

type
// define NCB structure
NCB = record
 ncb_command : AnsiChar;
 ...
end;

// Define function type
TNetBios=function(pncb : NCB): AnsiChar; stdcall;

var
  NetBios: TNetBios;
  Handle:THandle;
  ncbVar : NCB;
  ret : AnsiChar;
begin
// load the library
Handle:=LoadLibrary('netapi32.dll');
// check if it is loaded
if Handle<>0 then begin
  try
   // get the address of the function
   @NetBios := GetProcAddress(Handle, 'NetBios');
  // Fill NCB structure
  ncbVar.ncb_command := CHR(4);
  // ...
  // now call the function
  ret := NetBios(ncbVar);
 finally
  // unload the library
  FreeLibary(Handle);
 end;
end else begin
  // library not found
  ShowMessage('netapi32.dll not found!');
end;
end;

I'm not sure about ncbVar type. It also could be:
type
  PNCB = ^NCB;
  NCB = record
.....

var
  ncbVar : PNCB;
----
So you can try both declarations.
About netapi32.dll : it is a part of windows networking. If a computer has no network installed, perhaps there won't be such a dll.

Regards, Geo
0

Featured Post

Vote for the Most Valuable Expert

It’s time to recognize experts that go above and beyond with helpful solutions and engagement on site. Choose from the top experts in the Hall of Fame or on the right rail of your favorite topic page. Look for the blue “Nominate” button on their profile to vote.

Tackle projects and never again get stuck behind a technical roadblock.
Join Now