(Page 4 of 13 in this chapter)


2.3 Setting Up the CT Access Environment

Before you can call functions from the NaturalFax library, the application must initialize CT Access and open the NFX, FXM, and ADI services. Application setup for CT Access consists of the following steps:

  1. Initializing CT Access for the process

    
    
  2. Creating event queues

    
    
  3. Creating CTA contexts and attaching them to an event queue

    
    
  4. Opening services on each CTA context

You register services in the call to ctaInitialize by specifying the service and service manager names. Only the services initialized in the call to ctaInitialize may be opened by the application. The following code excerpt demonstrates CT Access initialization:

static DWORD initialize_base (void )
{
  CTA_SERVICE_NAME init_services [] =
    {
   { "ADI", "ADIMGR" },
   { "FXM", "ADIMGR" },
   { "NFX", "NFXMGR" },
    };
    CTA_INIT_PARMS init_parms =
  {
    sizeof (CTA_INIT_PARMS), 
  };
    DWORD status;
    static int initialized = 0;
 
    if (initialized)
   return SUCCESS;
  status = ctaInitialize (       init_services,
         sizeof init_services / sizeof init_services [0],
            & init_parms);
    if (status != SUCCESS)
   show_error (NULL_CTAHD, status, "CT Access initialization failed");
    else
   initialized = 1;
    return status;
}

2.3.1 Creating Event Queues and CTA Contexts

After initializing CT Access, you must create the event queues and CTA contexts.

Create one or more event queues by calling ctaCreateQueue. You specify which service managers will be attached to each queue. The NFX service manager is NFXMGR. The FXM and ADI service manager is ADIMGR. When you attach or bind a service manager to a queue, you make that service manager available to the queue.

Create a CTA context by calling ctaCreateContext. You provide the queue handle (ctaqueuehd) that was returned from ctaCreateQueue. All events for services on the CTA context will be received in the specified event queue.

ctaCreateContext returns a CTA context handle (ctahd). The CTA context handle is supplied by the application when invoking NaturalFax functions. Events communicated back to the application are also associated with the CTA context.

Refer to Chapter 3 in the CT Access Developer's Manual for details on the programming models created by the use of CTA contexts and queues.

2.3.2 Opening Services

Services are opened on a CTA context by calling ctaOpenServices, passing a CTA context handle and a list of service descriptors. The service descriptor specifies the name of the service, service manager, and service-specific arguments (e.g., MVIP address).

The NFX service must be opened on a CTA context in order to use NaturalFax's library of C functions. The NaturalFax (NFX) service does not require any service-specific arguments.

The Fax Manager service (FXM) service provides the hardware interface for the NaturalFax service. When opening the FXM service, the board, MVIP address, and mode are specified. When sending or receiving a fax, the NFX service will use the hardware resources (board and port) specified by the FXM service opened on the same CTA context.

In order to place and receive calls, the ADI service must be opened. The ADI service is opened with service-specific arguments such as AG board, MVIP address, and mode.

The following code excerpt demonstrates creating the CTA context and opening the NFX, FXM, and ADI services.

static DWORD create_context (CTAQUEUEHD queue,
        DWORD      board,
        DWORD      stream,
        DWORD      timeslot,
        DWORD      closure,
        char     * contextname,
        CTAHD    * contextptr)
{
    DWORD status;
    CTA_SERVICE_DESC services [3];
    DWORD service_count = 0;
    CTA_EVENT event;

    status = ctaCreateContext (queue, closure, contextname, contextptr);
    if (status != SUCCESS)
    {
   show_error (NULL_CTAHD, status, "CT Access context creation failed");
   return status;
    }
  
    /*
     * Now that we have a valid CT Access context, we can use ctaGetText
     * to get proper error messages.
     */

    memset (& services, 0, sizeof services);

  services[service_count].name.svcname      = "ADI";
    services[service_count].name.svcmgrname   = "ADIMGR";
    services[service_count].mvipaddr.board    = board;
    services[service_count].mvipaddr.stream   = stream;
    services[service_count].mvipaddr.timeslot = timeslot;
    services[service_count].mvipaddr.mode     = ADI_FULL_DUPLEX;
    service_count += 1;

    services[service_count].name.svcname      = "FXM";
    services[service_count].name.svcmgrname   = "ADIMGR";
    services[service_count].mvipaddr.board    = board;
    services[service_count].mvipaddr.stream   = stream;
    services[service_count].mvipaddr.timeslot = timeslot;
    services[service_count].mvipaddr.mode     = ADI_FULL_DUPLEX;
    service_count += 1;
  services[service_count].name.svcname      = "NFX";
    services[service_count].name.svcmgrname   = "NFXMGR";
    services[service_count].mvipaddr.board    = board;
    services[service_count].mvipaddr.stream   = stream;
    services[service_count].mvipaddr.timeslot = timeslot;
    services[service_count].mvipaddr.mode     = ADI_FULL_DUPLEX;
    service_count += 1;

    status = ctaOpenServices (* contextptr, services, service_count);
    if (status != SUCCESS)
    {
   show_error (* contextptr, status, "open services failed");
   return status;
    }

    /* Now we need to wait for the CTAEVN_OPEN_SERVICES_DONE event. */
    status = wait_event (queue, * contextptr, CTAEVN_OPEN_SERVICES_DONE,
        NULL, 0, & event);
    if (status != SUCCESS)
    {
   show_error (* contextptr, status, "open services failed");
   return status;
    }
    else if (event.value != CTA_REASON_FINISHED)
    {
   show_error (* contextptr, event.value, "open services done event");
   return event.value;
    }
    else
   return SUCCESS;
}


(Page 4 of 13 in this chapter)


tech_support@nmss.com
Copyright © 1997, Natural MicroSystems, Inc. All rights reserved.