Sun Java System Web Proxy Server 4.0.11 NSAPI Developer's Guide

Chapter 5 Data Structure Reference

NSAPI uses many data structures that are defined in the nsapi.h header file, which is in the directory server-root/plugins/include.

The NSAPI functions described in Chapter 4, NSAPI Function Reference provide access to most of the data structures and data fields. Before directly accessing a data structure in naspi.h, check whether an accessor function exists for that structure.

For information about the privatization of some data structures in Sun Java System Web Proxy Server 4, see Privatization of Some Data Structures

The rest of this chapter describes public data structures in nsapi.h. Data structures in nsapi.h that are not described in this chapter are considered private and might change incompatibly in future releases.

This chapter contains the following sections:

Privatization of Some Data Structures

The data structures in nsapi_pvt.h are now considered to be private data structures. Do not write code that accesses them directly. Instead, use accessor functions. This change should have very little impact on customer-defined plug-ins. Examine nsapi_pvt.h to see which data structures have been removed from the public domain. You can also see the accessor functions you can use now to access these dat structures.

plug-ins written for Enterprise Server 3.x that access contents of data structures defined in nsapi_pvt.h will not be source compatible with Sun Java System Web Proxy Server 4 you will have to #include "nsapi_pvt.h" to build such plug-ins from source. These programs might not be binary compatible with Sun Java System Web Proxy Server 4, because some of the data structures in nsapi_pvt.h have changed size. In particular, the directive structure is larger, which means that a plug-in that indexes through the directives in a dtable will not work without being rebuilt with nsapi_pvt.h included.

Because the majority of plug-ins do not reference the internals of data structures in nsapi_pvt.h, most existing NSAPI plug-ins will be both binary and source compatible with Sun Java System Web Proxy Server 4.

plug-ins written for iPlanet Web Proxy Server 3.6 will not be binary compatible with Proxy Server 4. These plug-ins will have to be recompiled and relinked using Web Proxy Server 4’s NSAPI header files and libraries.


A session is the time between the opening and closing of the connection between the client and the server. The session data structure holds variables that apply session wide, regardless of the requests being sent, as shown in the following example.

typedef struct {
/* Information about the remote client */
    pblock *client;

    /* The socket descriptor to the remote client */
    SYS_NETFD csd;

    /* The input buffer for that socket descriptor */
    netbuf *inbuf;

    /* Raw socket information about the remote */
    /* client (for internal use) */
    struct in_addr iaddr;
} Session;



The parameter block is the hash table that holds pb_entry structures. Its contents are transparent to most code. This data structure is frequently used in NSAPI. It provides the basic mechanism for packaging up parameters and values. Many functions exist for creating and managing parameter blocks, and for extracting, adding, and deleting entries. See the functions whose names start with pblock_ in Chapter 4, NSAPI Function Reference. You should not need to write code that accesses pblock data fields directly.

typedef struct {
    int hsize;
    struct pb_entry **ht;
} pblock;



The pb_entry is a single element in the parameter block.

struct pb_entry {
    pb_param *param;
    struct pb_entry *next;



The pb_param represents a name-value pair, as stored in a pb_entry.

typedef struct {
    char *name,*value;
} pb_param;



The Session->client parameter block structure contains two entries:

/** session_dns returns the DNS host name of the client for this* session 
	and inserts it into the client pblock. Returns NULL if* unavailable.
	*/char *session_dns(Session *sn);


Under HTTP protocol, only one request is made per session. The request structure contains the variables that apply to the request in that session, for example, the variables include the client’s HTTP headers.

typedef struct {
    /* Server working variables */
    pblock *vars;

    /* The method, URI, and protocol revision of this request */
    block *reqpb;

    /* Protocol specific headers */
    int loadhdrs;
    pblock *headers;

    /* Server’s response headers */
    int senthdrs;
    pblock *srvhdrs;

    /* The object set constructed to fulfill this request */
    httpd_objset *os;
} Request;



When a program calls the stat( ) function for a given file, the system returns a structure that provides information about the file. The specific details of the structure should be obtained from your platform’s implementation, but the basic outline of the structure is shown in the following example.

struct stat {
    dev_t      st_dev;     /* device of inode */
    inot_t     st_ino;     /* inode number */
    short      st_mode;    /* mode bits */
    short      st_nlink;   /* number of links to file /*
    short      st_uid;     /* owner’s user id */
    short      st_gid;     /* owner’s group id */
    dev_t      st_rdev;    /* for special files */
    off_t      st_size;    /* file size in characters */
    time_t     st_atime;   /* time last accessed */
    time_t     st_mtime;   /* time last modified */
    time_t     st_ctime;   /* time inode last changed*/


The elements that are most significant for server plug-in API activities are st_size, st_atime, st_mtime, and st_ctime.


typedef struct {
    void       *data;   /* the data */
    HANDLE     fdmap;
    int        size;    /* the maximum length of the data */
    char       *name;   /* internal use: filename to unlink if exposed */
    SYS_FILE   fd;      /* internal use: file descriptor for region */
} shmem_s;



The cinfo data structure records the content information for a file.

typedef struct {
    char    *type;
            /* Identifies what kind of data is in the file*/
    char    *encoding;
             /* encoding identifies any compression or other /*
            /* content-independent transformation that’s been /*
            /* applied to the file, such as uuencode)*/
    char    *language;            
            /* Identifies the language a text document is in. */
} cinfo;



The sendfiledata data structure is used to pass parameters to the net_sendfile function. It is also passed to the sendfile method in an installed filter in response to a net_sendfile call.

typedef struct {
    SYS_FILE fd;         /* file to send */
    size_t offset;       /* offset in file to start sending from */
    size_t len;          /* number of bytes to send from file */
    const void *header;  /* data to send before file */
    int hlen;            /* number of bytes to send before file */
    const void *trailer; /* data to send after file */
    int tlen;            /* number of bytes to send after file */
} sendfiledata;



The Filter data structure is an opaque representation of a filter. A Filter structure is created by calling filter_create.

typedef struct Filter Filter;



The FilterContext data structure stores context associated with a particular filter layer. Filter layers are created by calling filter_insert.

Filter developers may use the data member to store filter-specific context information.

typedef struct {
    pool_handle_t *pool; /* pool context was allocated from */
    Session *sn;         /* session being processed */
    Request *rq;         /* request being processed */
    void *data;          /* filter-defined private data */
} FilterContext;



The FilterLayer data structure represents one layer in a filter stack. The FilterLayer structure identifies the filter installed at that layer. It provides pointers to layer-specific context and a filter stack that represents the layer immediately below it in the filter stack.

typedef struct {
    Filter *filter; /* the filter at this layer in the filter stack */
    FilterContext *context; /* context for the filter */
    SYS_NETFD lower; /* access to the next filter layer in the stack */
} FilterLayer;



The FilterMethods data structure is passed to filter_create to define the filter methods a filter supports. Each new FilterMethods instance must be initialized with the FILTER_METHODS_INITIALIZER macro. For each filter method a filter supports, the corresponding FilterMethods member should point to a function that implements that filter method.

typedef struct {
    size_t size;
    FilterInsertFunc *insert;
    FilterRemoveFunc *remove;
    FilterFlushFunc *flush;
    FilterReadFunc *read;
    FilterWriteFunc *write;
    FilterWritevFunc *writev;
    FilterSendfileFunc *sendfile;
} FilterMethods;


CacheEntry Data Structure

The CacheEntry data structure holds all the information about one cache entry. The structure is created by the ce_lookup function and destroyed by the ce_free function CacheEntry is defined in the libproxy/cache.h file.

typedef struct _CacheEntry {
    CacheState  state;    /* state of the cache file; DO NOT refer to any
                 * of the other fields in this C struct if state
                 * is other than
                 *        CACHE_REFRESH or
                 *        CACHE_RETURN_FROM_CACHE
SYS_FILE    fd_in;    /* do not use: open cache file for reading */
int fd_out;    /* do not use: open (locked) cache file for writing */
struct stat finfo;    /* stat info for the cache file */
unsigned char  digest[CACHE_DIGEST_LEN];    /* MD5 for the URL */
char *         url_dig;  /* URL used to for digest; field #8 in CIF */
char *        url_cif;   /* URL read from CIF file */
char *        filname;   /* Relative cache file name */
char *        dirname;   /* Absolute cache directory name */
char *        absname;   /* Absolute cache file path */
char *        lckname;   /* Absolute locked cache file path */
char *        cifname;   /* Absolute CIF path */
int        sect_idx;     /* Cache section index */
int        part_idx;     /* Cache partition index */
CSect *        section;  /* Cache section that this file belongs to */
CPart *        partition;/* Cache partition that this file belongs to */
int         xfer_time;   /* secs *//* Field #2 in CIF */
time_t         last_modified;/* GMT *//* Field #3 in CIF */
time_t         expires;      /* GMT *//* Field #4 in CIF */
time_t         last_checked; /* GMT *//* Field #5 in CIF */
long         content_length; /* Field #6 in CIF */
char *        content_type;  /* Field #7 in CIF */
int        is_auth;          /* Authenticated data -- always do recheck */
int        auth_sent;        /* Client did send the Authorization header */
long    min_size;            /* Min size for a cache file (in KB) */
long    max_size;            /* Max size for a cache file (in KB) */
time_t         last_accessed;/* GMT for proxy, local for gc */
time_t        created;       /* localtime (only used by gc, st_mtime) */
int        removed;          /* gc only; file was removed from disk */
long        bytes;           /* from stat(), using this we get hdr len */
long        bytes_written;   /* Number of bytes written to disk */
long        bytes_in_media;  /* real fs size taken up */
long        blks;            /* size in 512 byte blocks */
int        category;         /* Value category; bigger is better */
int        cif_entry_ok;     /* CIF entry found and ok */
time_t ims_c;                /* GMT; Client -> proxy if-modified-since */
time_t        start_time;    /* Transfer start time */
int         inhibit_caching; /* Bad expires/other reason not to cache */
int corrupt_cache_file;      /* Cache file gone corrupt => remove */
int     write_aborted;       /* True if the cache file write was aborted */
int batch_update;    /* We’re doing batch update (no real user) */
char *        cache_exclude; /* Hdrs not to write to cache (RE) */
char *        cache_replace; /* Hdrs to replace with fresh ones 
										from 304 response (RE) */
char *        cache_nomerge; /* Hdrs not to merge with the 
										cached ones (RE) */
Session *     sn;
Request *     rq;
} CacheEntry;

CacheState Data Structure

The CacheState data structure is actually an enumerated list of constants. Aways use the constant names because values are subject to implementation change.

typedef enum {
CACHE_EXISTS_NOT = 0,        /* Internal flag -- do not use! */
CACHE_EXISTS,                /* Internal flag -- do not use! */
CACHE_NO,                    /* No caching: don’t read, don’t write cache */
CACHE_CREATE,                /* Create cache; don’t read */
CACHE_REFRESH,               /* Refresh cache; read if not modified */
CACHE_RETURN_FROM_CACHE,     /* Return directly, no check */
CACHE_RETURN_ERROR           /* With connect-mode=never when not in cache */
} CacheState;

ConnectMode Data Structure

The ConnectMode data structure is actually an enumerated list of constants. Always use the constant names because values are subject to implementation change.

typedef enum {
CM_NORMAL = 0,            /* normal -- retrieve/refresh when necessary */
CM_FAST_DEMO,            /* fast -- retrieve only if not in cache already */
CM_NEVER            /* never -- never connect to network */
} ConnectMode;