Below is an example. While PL_option_t is a struct, its 
members are initialised using the PL_OPTION() macro. The data 
structure is not constant because PL_scan_options() 
adds the option names as
atoms to speed up option processing. The macro PL_OPTIONS_END 
terminates the option list.
static PL_option_t mypred_options[] =
{ PL_OPTION("quoted",   OPT_BOOL),
  PL_OPTION("length",   OPT_SIZE),
  PL_OPTION("callback", OPT_TERM),
  PL_OPTIONS_END
};
static foreign_t
mypred(term_t a1, term_t options)
{ int    quoted   = FALSE;
  size_t length   = 10;
  term_t callback = 0;
  if ( !PL_scan_options(options, 0, "mypred_options", mypred_options,
                        "ed, &length, &callback) )
    return FALSE;
  <implement mypred>
}
The only defined value for flags is currently OPT_ALL, 
which causes this function to raise a domain error if an option is 
passed that is not in specs. Default in SWI-Prolog is to 
silently ignore unknown options, unless the Prolog flag iso 
is true. The opttype argument defines the type 
(group) of the options, e.g., "write_option". Option types 
are defined by the ISO standard. SWI-Prolog only uses this if OPT_ALL 
is specified, to raise a domain_error of the indicated type 
if some option is unused. The type name is normally the name of the 
predicate followed by
_option or the name of a representative of a group of 
predicates to which the options apply.
Defined option types and their corresponding pointer type are described below.
OPT_BOOL intTRUE.OPT_INT intOPT_INT64 int64_tOPT_UINT64 uint64_tOPT_SIZE size_tOPT_DOUBLE doubleOPT_STRING char*CVT_ALL|REP_UTF8|BUF_STACK|CVT_EXCEPTION. The buffered 
string must be guarded using PL_STRINGS_MARK() 
and PL_STRINGS_RELEASE().OPT_ATOM atom_tOPT_TERM term_tThe ISO standard demands that if an option is repeated the last occurance holds. This implies that PL_scan_options() must scan the option list to the end.