B.8.4 Using Paired NetBIOS Providers
A NetBIOS provider must closely couple its connection-oriented services with its connectionless services. However, through TPI, a STREAMS stack must declare itself as either a connection-oriented (T_COTS) or a connectionless (T_CLTS) provider. Therefore a STREAMS NetBIOS provider has to be implemented via two drivers: a T_COTS driver and a T_CTLS driver. For example, NetBIOS over TCP/IP is provided by the following STREAMS drivers:
\device\streams\nbt
\device\streams\nbdg
Example: DriverEntry Routine for nbt.sys
#include <ntddk.h>
#include <tdi.h>
#include <stream.h>
#include <xti.h>
**********************
extern struct streamtab nbtinfo, nbdginfo;
static struct nbaddr BroadcastName = {
NBBROADCAST | NBGROUPNM,
"*"
};
static STREAMS_TDI_ADDRESS_INFO AddressInfo = {
sizeof(BroadcastName), // Broadcast address length
TDI_ADDRESS_TYPE_NETBIOS, // TDI address type
TRUE, // Directed message goes farther
// than broadcast or multicast
&BroadcastName // Broadcast address
};
STREAMS_TDI_INFO NbtTdiInfo = {
T_COTS_ORD, // SERV_type
&nbdginfo, // Partner streamtab
T_CLTS, // Partner SERV_type
0, // Option length
NULL, // Option pointer
TRUE, // Reuseaddr set by default
1, // One address info structure
&AddressInfo // AddressInfo
};
STREAMS_TDI_INFO NbdgTdiInfo = {
T_CLTS, // SERV_type
&nbtinfo, // Partner streamtab
T_COTS_ORD, // Partner SERV_type
0, // Option length
NULL, // Option pointer
TRUE, // Reuseaddr set by default
1, // One address info structure
&AddressInfo // AddressInfo
};
NTSTATUS
DriverEntry(
IN PDRIVER_OBJECT driver,
PUNICODE_STRING description
)
{
NTSTATUS status;
status = ExtractRegistry();
if (status != STATUS_SUCCESS) {
return(status);
}
if (nbtinit()) {
return(STATUS_NO_MEMORY);
}
status = StrmRegisterDriver(driver, &nbtinfo, NULL, &NbtTdiInfo);
if (status != STATUS_SUCCESS) {
return(status);
}
status = StrmRegisterDriver(driver, &nbdginfo, NULL, &NbdgTdiInfo);
if (status != STATUS_SUCCESS) {
return(status);
}
return(status);
}