Write and Compile the ODL File

This chapter explains how to write and compile a JUNOS output definition language (ODL) file. It assumes that you are familiar with the statements described in detail in the preceding chapters, Define Tags and Create Formatting Instructions for the CLI Renderer. It has the following sections:

Create the ODL File

The ODL file for a JUNOS module is an ASCII-format text file that includes statements of the type described in Define Tags and Create Formatting Instructions for the CLI Renderer, plus a brief preamble. To create it, use any word processing program that generates plain ASCII (with no program-specific or hidden formatting markers). After the ODL file is complete, you compile it by using the ODL compiler (odc) as described in Compile the ODL File.

The conventional name for an ODL file is information-type.odl, where information-type indicates the type of information to which the tags apply. For example, the name of the file for interface information is interface.odl, and the name of the file for chassis-related information is chassis.odl.

For more information about creating the ODL file, see the following sections:

Create the DTD

Begin the ODL file with a preamble comment that contains a copyright plus any version control keywords (for example, $Id$) in use at your site. Then create another comment to specify the type of information the DTD contains. The following example illustrates these preamble comments.

 /*
  * $Id: chassis.odl,v 1.119 2006/10/10 21:26:48 Exp $
  *
  * ODL description of chassis information.
  *
  * Copyright (c) 2000-2006, Juniper Networks, Inc.
  * All rights reserved.
  */

 /*
  * This odl file defines a dtd called junos-chassis.
  */

Next, create a dtd statement to define the name of the document type definition (DTD) file that the ODL compiler derives from this ODL file. The conventional name for JUNOS DTD files is information-type.dtd, where information-type indicates the type of data to which the tags apply. For example, the name of the DTD for interface information is interface.dtd, and the name for chassis-related information is chassis.dtd.

The following statement illustrates the conventional format for the DTD. Substitute the type of data for the information-type variable (for example, interface or chassis). Notice that the filename in the dtd statement does not include the .dtd extension because the ODL compiler adds it automatically. Notice also that the dtd statement ends with a semicolon, as do all single-line statements in an ODL file.

dtd information-type;

Create a Tag Statement for Each Operational Response Tag

After the dtd statement, create statements specific to the information you are tagging. By convention, you create a separate container tag for the output from each JUNOS show command (hereafter referred to as operational response tags). For example, in the ODL file called chassis.odl (which is for the show chassis family of commands), there is a container tag called <chassis-inventory> for the output from the show chassis hardware command and another called <environment-information> for the output from the show chassis environment command.

Every document or data set tagged with XML tags has a single root, or top-level container, tag that contains all other tags that can occur in the document or data set. Each set of output returned by a JUNOS module in response to a client’s request is a complete XML (and specifically JUNOScript) document, and so must have a root tag. The root tag for all JUNOScript-tagged output is <rpc-reply>, so called because JUNOS modules generally return data in response to an RPC request.

The generic JUNOScript library created by the user interface team already defines <rpc-reply> as the root tag for JUNOScript-tagged data sets, so you do not need to redefine the tag in your ODL file. You simply need to create your own single root tag per operational response. These root tags are marked by flagging them as root.

The following example from the chassis.odl file defines two operational response tags. The statements for a command tag’s children are conventionally nested within it. They are omitted here to make the overall structure more obvious.

   /*
   * Hardware inventory ("show chassis hardware" command)
   */ 
   tag chassis-inventory {	
      flag root;
      # additional code
   }
   
   /*
    * Environment ("show chassis environment" command)
   */ 
   tag environment-information {	
      flag root;
      # additional code
   } 

Create Statements for Nested Tags

Within the tag statement for an operational response tag you nest the tag statements for the container and simple tags that the JUNOS module uses to mark the data it returns. To learn how to create tag statements, see Define Tags. An operational response tag normally also contains a format statement to define how the JUNOS command-line interface (CLI) renderer displays the child tags returned with the operational response tag. For information on how to control format issues, See Create Formatting Instructions for the CLI Renderer.

About the Namespace Attribute

Each JUNOS module’s ODL file (and resulting DTD) constitutes a separate XML namespace for the set of tags it contains. Establishing separate namespaces means that a tag in your DTD can have the same name as a tag in another DTD without causing ambiguity.

The ODL compiler derives the name of the XML namespace from the DTD name defined by the dtd statement in the ODL file, which is discussed in Create the DTD. When the odc command line includes the –u option, the ODL compiler records the namespace name in a #define statement in the module’s module_odl.h file. The #define statement has the following format. The value for release is hardcoded for each release by the user interface team.

#define XML_NS http://xml.juniper.net/junos/release/dtd_name

The #define statement defines the XML namespace for each operational response tag defined in the dtd_name.dtd file. By convention, your module includes the standard XML attribute called xmlns in the header of each operational response tag it emits, to define the tag’s namespace. For instructions, see Assign the xmlns Attribute.

As an example, the <interface-information> tag is from the junos-interface.dtd file, so its xmlns attribute has the following value in the initial release of JUNOS Release 9.3:

xmlns="http://xml.juniper.net/junos/9.3R1/junos-interface"

Compile the ODL File

After you finish writing the ODL file, you process the standard ODL Makefile, file, which invokes the odc command to compile the ODL file. See the instructions in the following sections:

Move the ODL File to the Input Directory

In preparation for compiling your ODL file, perform the following steps.

  1. Copy or move your ODL source file to the sandbox/src/lib/odl/input directory, where the ODL source files for all JUNOS modules are stored.

  2. Edit or create the information-type.input.mk file stored there, adding your ODL file to the list of files for the relevant module, which begins with the following header. If your ODL file is the first one for its module, you must create the header as well as the entry in the list of features.

    module_INPUT_FEATURES += module
    module_INPUT_FILES = \
    

    Place your ODL file on its own line in the list. Following standard Makefile syntax, each line ends with a backslash ( \ ) except the final one. As an example, the entry for the chassis.odl file is as follows:

    chassis_INPUT_FILES = \
            chassis.odl
    

Invoke the ODL Makefile

To compile your ODL file, invoke the mk command, which automaticaly invokes the odc command. You can do this in the odl directory or in the src directory.

The odc command in the standard ODL Makefile file includes options that generate the following files and libraries in sandbox/obj-i386/lib/odl/xmltags.

Link with the Static Library

In your application’s Makefile file, which resides in the sandbox/src/sbin/application directory, add a variable to the DPLIBS list that points to your libmodule-odl.a file. This variable should be defined in the sandbox/src/share/mk/libnames.mk file. An example of the correct variable definition format is as follows:

LIBMODULE-ODL = ${_OBJTOP}/lib/odl/xmltags/libmodule-odl.a

Ship the Renderer Library

As the final step in compiling the ODL file, add an entry for the shared library to your application’s package manifest file, which resides in the sandbox/src/release directory. For an example of the correct entry format, see the JUNOS SDK sample applications.

Syntax of the odc Command

The odc command has the following syntax:

odc -i module_id -m module [-c] [-d] [-r] [-u] [-v] [-x] odl_file 

-c Run the ODL file through the C preprocessor also, which converts define statements in the ODL file into C #define statements as described in enum Type and Specify a Tag Index Name in Library Files.
-d Write the data structures used by the ODL compiler during compilation to stdout, for debugging purposes.
-i module_id Assign the specified identifier module_id to the data structures that are generated for the renderer when the -r option is included. The ODL Makefile file includes a module identifier statement that defines this value for each module. By convention, the identifiers start with the prefix DAE_. They are listed in the junos/include/jnx/daemon_info.h file.
-m module Use the specified module name as the variable part of the names for files generated by the compilation, such as module_odl.c. The ODL compiler selects the appropriate value from the FEATURES list in the ODL Makefile file.
odl_file The ODL filename, complete with .odl extension.
-r Generate the module_render.c file, which contains the data structures used by the CLI renderer to display JUNOScript-tagged output.
-u Generate the module_odl.c and module_odl.h files. The first is used to build the user library file, libmodule-odl.a, and the second contains the data structures used by the module and other user programs when they emit JUNOScript-tagged output.
-v Include comments in the DTD as described in Specify a Tag Index Name in Library Files.
-x Generate a DTD.

As an example, the following command is appropriate for the JUNOS chassis.odl file:

odc -m chassis -i DAE_CHASSISD -d -u -c -r -v -x chassis.odl

This command produces the following output files in the current working directory:

The Makefile file includes additional commands that generate the following library files, also in the current working directory:

To review the function of each file, see Invoke the ODL Makefile.
© 2007-2009 Juniper Networks, Inc. All rights reserved. The information contained herein is confidential information of Juniper Networks, Inc., and may not be used, disclosed, distributed, modified, or copied without the prior written consent of Juniper Networks, Inc. in an express license. This information is subject to change by Juniper Networks, Inc. Juniper Networks, the Juniper Networks logo, and JUNOS are registered trademarks of Juniper Networks, Inc. in the United States and other countries. All other trademarks, service marks, registered trademarks, or registered service marks are the property of their respective owners.
Generated on Sun May 30 20:26:47 2010 for Juniper Networks Partner Solution Development Platform JUNOS SDK 10.2R1 by Doxygen 1.4.5