Retired Document
Important: This sample code may not represent best practices for current development. The project may use deprecated symbols and illustrate technologies and techniques that are no longer recommended.
TPIFileTest.c
/* |
File: TPIFileTest.c |
Contains: A trivial test program for the TPIFile module. |
Written by: Quinn "The Eskimo!" |
Copyright: © 1997 by Apple Computer, Inc., all rights reserved. |
Change History (most recent first): |
You may incorporate this sample code into your applications without |
restriction, though the sample code has been provided "AS IS" and the |
responsibility for its operation is 100% yours. However, what you are |
not permitted to do is to redistribute the source as "DSC Sample Code" |
after having made changes. If you're going to re-distribute the source, |
we require that you make it clear in the source that the code was |
descended from Apple Sample Code, but that you've made changes. |
*/ |
///////////////////////////////////////////////////////////////////// |
// Pick up all the OT client info, specifically the OTRegisterPort. |
#include <OpenTransport.h> |
#include <Events.h> |
///////////////////////////////////////////////////////////////////// |
// OK, so it's yet another console based sample from Quinn! |
#include <stdio.h> |
#include <limits.h> |
///////////////////////////////////////////////////////////////////// |
// Pick up the name of the TPIFile port. |
#include "TPIFile.h" |
///////////////////////////////////////////////////////////////////// |
// Define a global buffer to hold the data we're reading out of the file. |
// |
// Note the number of bytes that we read out of the endpoint in a single |
// hit is not the same chunk size as used by the TPIFile module to read |
// the file (which is 2KB). This is a deliberate test of the way OT |
// endpoint libraries do deblocking. |
enum { |
kBufferSize = 1000 |
}; |
static char gBuffer[kBufferSize]; |
///////////////////////////////////////////////////////////////////// |
static OSStatus TestTPIFile(ConstFSSpecPtr fss, UInt32 byteCount, Boolean disconnect) |
// Test the TPIFile module by opening an endpoint to the |
// file specified by fss and printing the contents to |
// the console window. |
{ |
OSStatus err; |
EndpointRef ep; |
TCall sndCall; |
FileSpecAddress connectAddr; |
OTFlags junkFlags; |
long i; |
// Open the endpoint to our module. |
ep = OTOpenEndpoint(OTCreateConfiguration(kTPIFilePortName), 0, nil, &err); |
// Switch to sync/blocking mode to simplify our code and then |
// do a null bind in preparation for the connect. |
if (err == noErr) { |
(void) OTSetBlocking(ep); |
(void) OTSetSynchronous(ep); |
err = OTBind(ep, nil, nil); |
} |
// Connect to a file specified by an AF_FILESPEC address format. |
if (err == noErr) { |
connectAddr.fAddressType = AF_FILESPEC; |
connectAddr.fss = *fss; |
sndCall.addr.buf = (UInt8 *) &connectAddr; |
sndCall.addr.len = sizeof(connectAddr); |
sndCall.opt.buf = nil; |
sndCall.opt.len = 0; |
sndCall.udata.buf = nil; |
sndCall.udata.len = 0; |
sndCall.sequence = 0; |
err = OTConnect(ep, &sndCall, nil); |
} |
// A standard OTRcv and print loop. |
if (err == noErr) { |
do { |
err = OTRcv(ep, gBuffer, kBufferSize, &junkFlags); |
if (err > noErr) { |
for (i = 0; i < err; i++) { |
if (byteCount == 0) { |
err = noErr; |
goto premature_close; |
} |
byteCount -= 1; |
if (gBuffer[i] == 13) { |
putchar(10); |
} else { |
putchar(gBuffer[i]); |
} |
} |
fflush(stdout); |
err = noErr; |
} |
} while (err == noErr); |
} |
premature_close: |
if (err == noErr && disconnect) { |
err = OTSndDisconnect(ep, nil); |
} |
// When we can't read any more data, consult and print the reason. |
if (err == kOTLookErr) { |
printf("Got kOTLookErr.\n"); |
err = OTLook(ep); |
switch (err) { |
case T_DISCONNECT: |
printf("T_DISCONNECT\n"); |
break; |
default: |
printf("Unknown look %d\n", err); |
} |
err = kOTLookErr; |
} |
if (ep != kOTInvalidEndpointRef) { |
(void) OTCloseProvider(ep); |
} |
return (err); |
} |
///////////////////////////////////////////////////////////////////// |
static OSStatus TestBogusConnect(void) |
// Test how well the TPI module handles being asked to connect |
// to a bogus FSSpec. |
{ |
OSStatus err; |
FSSpec bogusFileSpec; |
(void) FSMakeFSSpec(0, 0, "\pBogus Victim", &bogusFileSpec); |
err = TestTPIFile(&bogusFileSpec, 1024, false); |
return (err); |
} |
///////////////////////////////////////////////////////////////////// |
static OSStatus TestConnectAsync(ConstFSSpecPtr fss, Boolean disconnect) |
// Test an asynchronous connect operation followed immediately |
// by a disconnect. |
{ |
OSStatus err; |
EndpointRef ep; |
TCall sndCall; |
FileSpecAddress connectAddr; |
ep = OTOpenEndpoint(OTCreateConfiguration(kTPIFilePortName), 0, nil, &err); |
// Switch to sync/blocking mode to simplify our code and then |
// do a null bind in preparation for the connect. |
if (err == noErr) { |
(void) OTSetBlocking(ep); |
(void) OTSetSynchronous(ep); |
err = OTBind(ep, nil, nil); |
} |
// Connect to a file specified by an AF_FILESPEC address format. |
if (err == noErr) { |
(void) OTSetAsynchronous(ep); |
connectAddr.fAddressType = AF_FILESPEC; |
connectAddr.fss = *fss; |
sndCall.addr.buf = (UInt8 *) &connectAddr; |
sndCall.addr.len = sizeof(connectAddr); |
sndCall.opt.buf = nil; |
sndCall.opt.len = 0; |
sndCall.udata.buf = nil; |
sndCall.udata.len = 0; |
sndCall.sequence = 0; |
err = OTConnect(ep, &sndCall, nil); |
if (err == kOTNoDataErr) { |
err = noErr; |
printf("Connecting\n"); |
} |
} |
if ( (err == noErr) && disconnect) { |
err = OTSndDisconnect(ep, nil); |
if (err == noErr) { |
printf("Waiting for disconnect"); |
while ( OTGetEndpointState(ep) != T_IDLE ) { |
if ( TickCount() % 10 == 0 ) { |
printf("."); |
} |
} |
printf("\n"); |
} |
} |
if (ep != kOTInvalidEndpointRef) { |
(void) OTCloseProvider(ep); |
} |
return (err); |
} |
///////////////////////////////////////////////////////////////////// |
static OSStatus TestConnectAsyncWithExtraEndpoint(ConstFSSpecPtr fss, Boolean disconnect) |
{ |
OSStatus err; |
EndpointRef ep; |
char junkStr[256]; |
ep = OTOpenEndpoint(OTCreateConfiguration(kTPIFilePortName), 0, nil, &err); |
if (err == noErr) { |
err = TestConnectAsync(fss, disconnect); |
} |
if (err == noErr) { |
printf("Press return to continue.\n"); |
gets(junkStr); |
} |
return (err); |
} |
///////////////////////////////////////////////////////////////////// |
void main(void) |
{ |
OSStatus err; |
FSSpec fileToTest; |
char commandStr[256]; |
printf("Hello Cruel World!\n"); |
fflush(stdout); |
err = InitOpenTransport(); |
if (err == noErr) { |
// Hardwire this code to read a file called "Victim" in the |
// same folder as the application. |
err = FSMakeFSSpec(0, 0, "\pVictim", &fileToTest); |
if (err == noErr) { |
printf("a) Read and print all.\n"); |
printf("b) Read and print with premature close.\n"); |
printf("c) Read and print with premature disconnect.\n"); |
printf("d) Connect to a bogus file.\n"); |
printf("e) Connect async then fast close.\n"); |
printf("f) Connect async then fast disconnect.\n"); |
printf("g) Connect async then fast close with extra endpoint.\n"); |
printf("Enter the test you want to perform:\n"); |
gets(commandStr); |
switch (commandStr[0]) { |
case 'a': |
err = TestTPIFile(&fileToTest, ULONG_MAX, false); |
break; |
case 'b': |
err = TestTPIFile(&fileToTest, 1024, false); |
break; |
case 'c': |
err = TestTPIFile(&fileToTest, 1024, true); |
break; |
case 'd': |
err = TestBogusConnect(); |
break; |
case 'e': |
err = TestConnectAsync(&fileToTest, false); |
break; |
case 'f': |
err = TestConnectAsync(&fileToTest, true); |
break; |
case 'g': |
err = TestConnectAsyncWithExtraEndpoint(&fileToTest, false); |
break; |
default: |
printf("Huh?\n"); |
err = -1; |
break; |
} |
} |
CloseOpenTransport(); |
} |
if (err == noErr) { |
printf("Success.\n"); |
} else { |
printf("Failed with error %d.\n", err); |
} |
printf("Done. Press command-Q to Quit.\n"); |
} |
Copyright © 2003 Apple Computer, Inc. All Rights Reserved. Terms of Use | Privacy Policy | Updated: 2003-07-22