Federated Naming Service Programming Guide

Client

The scenario for Example 3-2 is a user who would like to print to a printer named colorful in his organization's context, thisorgunit/service/printer/colorful. The example printer client illustrates how the bindings for a specific printer are obtained.

The variable printer_binding contains the reference (the binding information) of the named printer. Using the binding information, the printer client can connect to the server and send the printer request. Note that the fn_ctx_lookup() function can be replaced by fn_ctx_list_name() or fn_ctx_list_bindings() to list all the names and their bindings.


Example 3-2 Print Client source


#include <stdio.h>
#include <xfn/xfn.h>
#include <string.h>
#include <stdlib.h>
 
/*
 * Routine to obtain the address of a specific printe.
 * This routine takes the printer name and the address type
 * as the input arguments and returns the address
 * of the requested printer.
 */
 
char *
get_address_of_printer(const char *printer_name,
	    const char *address_type)
{
   FN_composite_name_t *printer_name_comp;
   FN_status_t *status = fn_status_create();
   FN_ctx_t *initial_context;
   FN_ref_t *printer_ref;
   const FN_identifier_t *addr_id;
   const FN_ref_addr_t *address;
   char *addr_data; /* Return value */
 
   void *ip;
   size_t address_type_len, addr_len;
 
   /* Convert the printer name to a composite name */
   printer_name_comp = fn_composite_name_from_string(
      (const unsigned char *)printer_name);
 
   /* Get the initial context */
   initial_context = fn_ctx_handle_from_initial(0, status);
 
   /* Check status for any error messages */
   if (!fn_status_is_success(status)){
    fprintf(stderr,
         "Unable to obtain the initial context\n");
    return (0);
	}
  /* Perform a lookup for the printer name */
  printer_ref = fn_ctx_lookup(initial_context,
     printer_name_comp, status);
 
  /* Check status for any error messages */
  if (!fn_status_is_success(status)){
    fprintf(stderr, "Lookup failed on: %s\n",
        printer_name);
    return (0);
  }
 
  fn_ctx_handle_destroy(initial_context);
  fn_composite_name_destroy(printer_name_comp);
  address_type_len = strlen(address_type);
 
  /* Obtain the requested address from the address type */
  for (address = fn_ref_first(printer_ref, &ip);
     address != NULL;
     address = fn_ref_next(printer_ref, &ip)) {
         addr_id = fn_ref_addr_type(address);
         if (addr_id->length == address_type_len &&
            strncmp(address_type,
                (char *)addr_id->contents,
                address_type_len) == 0)
                break;
   }
  if (address == NULL)
      return (0);
  addr_len = fn_ref_addr_length(address);
  addr_data = (char *)(malloc(addr_len + 1));
  strncpy(addr_data,(char*)(fn_ref_addr_data(address)),
          addr_len);
  addr_data[addr_len] = '\0';
  fn_ref_destroy(printer_ref);
  return (addr_data);
}

Calling the Printer Client Function

The following code could be used to call the get_address_of_printer() routine shown above.


char* printer_server;
printer_server = get_address_of_printer
 
    "thisorgunit/service/printer/colorful",
 
    "onc_bsdaddr");