Plug-in Programmer’s Guide
Red Hat Directory Server                                                            

Previous
Contents
Index
Next

Chapter 10

Writing Extended Operation Plug-ins


This chapter explains how to write plug-in functions to handle extended operations. Extended operations are are defined in the LDAP v3 protocol.

The chapter contains the following sections:

How Extended Operation Plug-ins Work

You can define your own operation that you want the Red Hat Directory Server (Directory Server) to perform. If you create a custom extended operation, you assign an object identifier (OID) to identify that operation. LDAP clients request the operation by sending an extended operation request. Within the request, the client specifies:

When the Directory Server receives the request, the server calls the plug-in registered with the specified OID. The plug-in function has access to both the OID and the data in the client's request. The plug-in function can send back to the client a response containing an OID plus any additional data that might be needed.

In order to use extended operations, you need to configure both the Directory Server and the client so they understand the specific extended operation that you want performed.

Writing Extended Operation Functions

Like other plug-in functions, extended operation functions pass a single parameter block (Slapi_PBlock) and return an integer value, as shown in the following example declaration:

int my_ext_func( Slapi_PBlock *pb );
 

Extended operation functions should return a value of 0 if they are successful and a non-zero value if they are unsuccessful.

When the Directory Server receives an extended operation request, the front-end calls the extended operation function with the OID value specified in the request. The front-end makes the following information available to the extended function in the form of parameters in a parameter block.

Table 10-1 Extended Function Parameter Block Arguments  
Parameter ID
Data Type
Description
SLAPI_EXT_OP_REQ_OID
char *
Object ID (OID) of the extended operation specified in the request.
SLAPI_EXT_OP_REQ_VALUE
struct berval*
Value specified in the request.
SLAPI_EXT_OP_RET_OID
char *
Object ID (OID) that you want sent back to the client.
SLAPI_EXT_OP_RET_VALUE
struct berval*
Value that you want sent back to the client.

Typically, your function should perform an operation on the value specified in the SLAPI_EXT_OP_REQ_VALUE parameter. After the extended operation completes, your function should return a single value, according to the following:

Note

For a sample plug-in function (uncompiled C code) that implements an extended operation, check this file: server_root /plugins/slapd/slapi/examples/testextendedop.c


Registering Extended Operation Functions

As is the case with other server plug-in functions (see "Passing Data with Parameter Blocks," on page 38), extended operation functions are specified in a parameter block that you can set on server startup.

In your initialization function, you can call the slapi_pblock_set() function to set the SLAPI_PLUGIN_EXT_OP_FN parameter to your function and the SLAPI_PLUGIN_EXT_OP_OIDLIST parameter to the list of OIDs of the extended operations supported by your function.

You can write your initialization function so that the OID is passed in from the directive. (See "Passing Extra Arguments to Plug-ins," on page 52, for details.) For example, the following initialization function sets the SLAPI_PLUGIN_EXT_OP_OIDLIST parameter to the additional parameters specified.

Code Example 10-1 Sample Initialization Function for Passing an OID  
 
int extended_init( Slapi_PBlock *pb )
{
  int i;
  char **argv;
  char **oids;
 
/* Get the additional arguments specified in the directive */
  if ( slapi_pblock_get( pb, SLAPI_PLUGIN_ARGV, &argv ) != 0 ) {
    slapi_log_error( SLAPI_LOG_PLUGIN, "extended_init",
    "Server could not get argv.\n" );
    return( -1 );
  }
  if ( argv == NULL ) {
    slapi_log_error( SLAPI_LOG_PLUGIN, "extended_init",
    "Required argument <oiD> is missing\n" );
    return( -1 );
  }
 
  /* Get the number of additional arguments and copy them. */
  for ( i = 0; argv[i] != NULL; i++ )
    ;
  oids = (char **) slapi_ch_malloc( (i+1) * sizeof(char *) );
  for ( i = 0; argv[i] != NULL; i++ ) {
    oids[i] = slapi_ch_strdup( argv[i] );
  }
  oids[i] = NULL;
/* Specify the version of the plug-in */
    if ( slapi_pblock_set( pb, SLAPI_PLUGIN_VERSION,
      SLAPI_PLUGIN_VERSION_01 ) != 0 ||
 
/* Specify the OID of the extended operation */
    slapi_pblock_set( pb, SLAPI_PLUGIN_EXT_OP_OIDLISTs,
      (void*) oids ) != 0 ||
 
/* Specify the function that the server should call */
    slapi_pblock_set( pb, SLAPI_PLUGIN_EXT_OP_FN,
      (void*) extended_op ) != 0 ) {
 
      slapi_log_error( SLAPI_LOG_PLUGIN, "extended_init",
      "An error occurred.\n" );
      return( -1 );
    }
  slapi_log_error( SLAPI_LOG_PLUGIN, "extended_init",
    "Plug-in sucessfully registered.\n" );
  return(0);
}
 

Depending on the Directory Server version, add a directive in the appropriate form to specify the name and location of your plug-in function and to specify the object identification (OID) of the operation.

In current releases of Directory Server, shut down the server, add the plug-in parameters to the dse.ldif file, and restart the server (see Chapter 3, "Configuring Plug-ins"). For example, your plug-in entry might look like this:

dn: cn=Test ExtendedOp,cn=plugins,cn=config

objectClass: top

objectClass: nsSlapdPlugin

objectClass: extensibleObject

cn: Test ExtendedOp

nsslapd-pluginPath: /opt/redhat-ds/servers/plugins/slapd/slapi/

	examples/libtest-plugin.so

nsslapd-pluginInitfunc: testexop_init

nsslapd-pluginType: extendedop

nsslapd-pluginEnabled: on

nsslapd-plugin-depends-on-type: database

nsslapd-pluginId: test-extendedop

nsslapd-pluginarg0: 1.2.3.4
 

For an example plug-in function that implements an extended operation, take a look at this source file:

server_root /plugins/slapd/slapi/examples/testextendedop.c
 

Specifying Start and Close Functions

For each extended operation plug-in, you can specify the name of a function to be called after the server starts and before the server is shut down.

Use the following parameters to specify these functions:

SLAPI_PLUGIN_START_FN
Specifies the function called after the Directory Server starts up.
SLAPI_PLUGIN_CLOSE_FN
Specifies the function called before the Directory Server shuts down.

If you register multiple plug-ins with different start and close functions, the functions are called in the order that the plug-ins are registered (in other words, in the order that the plugin directives appear in the server configuration file).




Previous
Contents
Index
Next

© 2001 Sun Microsystems, Inc. Used by permission. © 2005 Red Hat, Inc. All rights reserved.
Read the Full Copyright and Third-Party Acknowledgments.

last updated May 26, 2005