/*
* $Id: epr_bitmask.h,v 1.2 2012/03/01 15:56:10 pascal Exp $
*
* Copyright (C) 2002 by Brockmann Consult (info@brockmann-consult.de)
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation. This program is distributed in the hope it will
* be useful, but WITHOUT ANY WARRANTY; without even the implied warranty
* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
#ifndef EPR_BITMASK_H_INCL
#define EPR_BITMASK_H_INCL
#ifdef __cplusplus
extern "C"
{
#endif
#define FLAG_MASK_NOT_COMPUTED ((ulong) -1)
typedef struct EPR_BmTerm EPR_SBmTerm;
typedef struct EPR_BmEvalContext EPR_SBmEvalContext;
typedef struct EPR_BmFlagDataset EPR_SBmFlagDataset;
typedef enum EPR_BmOpCode EPR_EBmOpCode;
/* private implementations */
enum EPR_BmOpCode {
BMT_UNKNOWN = 0,
BMT_REF,
BMT_AND,
BMT_OR,
BMT_NOT
};
enum EPR_Tok {
BME_UNKNOWN = 0,
BME_EOS,
BME_SPECIAL,
BME_NAME
};
/**
* The EPR_BmTerm
structure is the union of structures:
* each of them can contain either the subject (operand) for the logic operators
* or this operators itself with referd operand(s). Thus they are recursive.
* The example of term: flags.WATER or flags.LAND
* here: 'flags' is a band_name; 'WATER' and 'LAND' - flag_name's; 'or' - logical operator.
*
* @see EPR_SRaster
*/
struct EPR_BmTerm {
EPR_EBmOpCode op_code;
union {
struct /*BMT_REF*/ {
char* band_name;
char* flag_name;
ulong flag_mask;
EPR_SRaster* flag_raster;
} ref;
struct /*BMT_NOT*/ {
EPR_SBmTerm* arg;
} unary;
struct /*BMT_AND and BMT_OR*/ {
EPR_SBmTerm* arg1;
EPR_SBmTerm* arg2;
} binary;
} op;
};
/**
* The EPR_BmEvalContext
structure represents an evaluation context for bitmask
* expressions. It is used internally only.
*
* An instance of this structure holds the product ID, references to all flag datasets
* required to evaluate the expression as well as information about the bitmask raster beeing
* created.
*
* @see EPR_SProductId
* @see EPR_SRaster
* @see EPR_SPtrArray
*/
struct EPR_BmEvalContext
{
/**
* The ID of the product to which this band belongs to.
*/
EPR_SProductId* product_id;
/**
* X-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster.
*/
int offset_x;
/**
* Y-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster.
*/
int offset_y;
/**
* The result 0/1 bit mask raster for all flag bands
*/
EPR_SRaster* bitmask_raster;
/**
* The band_id of flags (can be 0, 1 or 4 - for AATSR)
*/
EPR_SPtrArray* flag_band_ids;
/**
* The corresponding 0/1 bit mask raster for each flag bands
*/
EPR_SPtrArray* flag_rasters;
};
/**
* Represents a flag-field within a flag-record.
*
*/
struct EPR_BmFlagDataset {
/*The name of bitmask dataset*/
char* name;
/*The value of bitmask dataset (the number of the relevant bit in bitmask)*/
uint bit_index;
/*The description of bitmask dataset*/
char* description;
};
/**
* Creates bit-mask evaluation context
* for the given raster and offsets of start corner
*
* @param product_id the product ID
* @param offset_x X-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster to search
* @param offset_y Y-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster to search
* @param raster the bitmask_raster
*
* @return bit-mask evaluated context for success, and error code otherwise
*/
EPR_SBmEvalContext* epr_create_bm_eval_context(EPR_SProductId* product_id,
int offset_x,
int offset_y,
EPR_SRaster* raster);
/**
* Release the memory allocated through a EPR_SBmEvalContext.
*
* @param context the bit mask context, if NULL
the function
* immediately returns zero.
* @return zero for success, an error code otherwise
*/
void epr_free_bm_eval_context(EPR_SBmEvalContext* context);
/**
* Reads bit-mask pixels of the given product for the given bit-mask expression
* for the given region and and with the given sub-sampling.
*
*
** *bit-mask-expression :=
* or-expression * *or-expression :=
* and-expression
* or-expressionor
and-expression * *and-expression :=
* not-expression
* and-expressionand
not-expression * *not-expression :=
* primary-expression
*not
not-expression * *primary-expression :=
* flag-reference
*(
bit-mask-expression)
* *flag-reference :=
* dataset-name.
flag-name *
Where dataset-name and flag-name are names specific for a particular data product. * Names are in general resolved case-insenitively. The parser also accepts an alternate notation for * the boolean operators: *
* The* * @param product_id the product ID * @param bm_expr the bit-mask expression * @param xo X-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster to search * @param yo Y-coordinate in pixel co-ordinates (zero-based) of the upper right corner raster to search * @param raster_width the width in pixel co-ordinates of the raster to search * @param raster_height the height in pixel co-ordinates of raster to search * @param s_x X-step in pixel co-ordinates to get the next raster to search * @param s_y Y-step in pixel co-ordinates to get the next raster to search * @param raster_buffer [BYTE] the memory buffer to save information was read * * @return zero for success, and error code otherwise */ int epr_read_bitmask_data(const EPR_SProductId* product_id, const char* bm_expr, int xo, int yo, int raster_width, int raster_height, int s_x, int s_y, void* raster_buffer); /** * Evaluates the given bitmask expression. * * @param term the bitmask term * @param x the x co-ordinate in pixels * @param y the y co-ordinate in pixels */ boolean epr_eval_bm_term(EPR_SBmEvalContext* context, EPR_SBmTerm* term, int x, int y); /** * Parses a bitmask expression string. * *|
character for theor
operator,
* the&
character for theand
operator and finally
* the!
character for thenot
operator. *
The bit-mask expressions recognized by this parser must have the following syntax: * *
** *bit-mask-expression :=
* or-expression * *or-expression :=
* and-expression
* or-expressionor
and-expression * *and-expression :=
* not-expression
* and-expressionand
not-expression * *not-expression :=
* primary-expression
*not
not-expression * *primary-expression :=
* flag-reference
*(
bit-mask-expression)
* *flag-reference :=
* dataset-name.
flag-name *
Where dataset-name and flag-name are names specific for a particular data product. * Names are in general resolved case-insenitively. The parser also accepts an alternate notation for * the boolean operators: *
* The* *|
character for theor
operator,
* the&
character for theand
operator and finally
* the!
character for thenot
operator. *
For example, the following parseBitmaskExpression request will perform without errors: *
* BitmaskTerm term = BitmaskExpressionParser.parse("flags.LAND and not flags.DDV"); **
Another example for a valid expression in alternatate notation is: *
* BitmaskTerm term = BitmaskExpressionParser.parse("flags.LAND | (flags.COASTLINE & !flags.CLOUD)"); ** *
The terms created in the examples above could successfully be evaluated in an evaluation context * provided by an ENVISAT MERIS Level 2 data product. * * @param bm_expr the bitmask expression * @return the bitmask term representing the given expression */ EPR_SBmTerm* epr_parse_bm_expr_str(const char* bm_expr); struct EPR_ParseInfo { const char* bm_expr; int bm_expr_pos; boolean pushed_back; int token_type; char* token; char* err_message; }; typedef struct EPR_ParseInfo EPR_SParseInfo; /** * This group of functions is for parsing the expression. * * @param parse_info parse_info structure * @param term_required the boolean value expression. * * @return the bit mask term (see EPR_BmTerm). */ /*@{*/ EPR_SBmTerm* epr_parse_bm_expr(EPR_SParseInfo* parse_info, boolean term_required); EPR_SBmTerm* epr_parse_bm_OR_expr(EPR_SParseInfo* parse_info, boolean term_required); EPR_SBmTerm* epr_parse_bm_AND_expr(EPR_SParseInfo* parse_info, boolean term_required); EPR_SBmTerm* epr_parse_bm_unary_expr(EPR_SParseInfo* parse_info, boolean term_required); EPR_SBmTerm* epr_parse_bm_primary_expr(EPR_SParseInfo* parse_info, boolean term_required); /*@}*/ /** * This group of functions is for recognizing the keyword. * * @param parse_info parse_info structure * * @return TRUE or FALSE. */ /*@{*/ boolean epr_is_bm_OR_keyword(EPR_SParseInfo* parse_info); boolean epr_is_bm_AND_keyword(EPR_SParseInfo* parse_info); boolean epr_is_bm_NOT_keyword(EPR_SParseInfo* parse_info); /*@}*/ /** * This group of functions is for recognizing the operator. * * @param parse_info parse_info structure * * @return TRUE or FALSE. */ /*@{*/ boolean epr_is_bm_AND_operator(EPR_SParseInfo* parse_info); boolean epr_is_bm_OR_operator(EPR_SParseInfo* parse_info); boolean epr_is_bm_NOT_operator(EPR_SParseInfo* parse_info); /*@}*/ /** * Tests the given expression for operand name only (not operator). * * @param parse_info parse_info structure * * @return TRUE if the term is not NULL and an operand, or FALSE otherwise */ boolean epr_is_bm_name_token(EPR_SParseInfo* parse_info); /** * Tests the given expression for the end of string. * * @param parse_info parse_info structure * * @return TRUE if the EOS occurs, or FALSE otherwise */ boolean epr_is_bm_EOS_token(EPR_SParseInfo* parse_info); /** * Tests the given expression for errors. * * @param parse_info parse_info structure * * @return TRUE if no error occurs, or FALSE otherwise */ boolean epr_is_bm_expr_error(EPR_SParseInfo* parse_info); /** * Gets the first character of token for the given expression or EOS. * * @param parse_info parse_info structure * * @return '(' , ')', '.' , '&' , '|' ,'!', or '\0' otherwise */ int epr_get_token_char(EPR_SParseInfo* parse_info); /** * Releases the actual token given expression. * * @param parse_info parse_info structure * * @return token */ char* epr_consume_token(EPR_SParseInfo* parse_info); /** * Selectss the next token given expression. * * @param parse_info parse_info structure */ void epr_next_bm_expr_token(EPR_SParseInfo* parse_info); void epr_push_back_bm_expr_token(EPR_SParseInfo* parse_info); void epr_set_bm_expr_error(EPR_SParseInfo* parse_info, const char* message); int epr_tokenize_bm_expr(const char* bm_expr, int* bm_expr_pos, char** token); /** * Creates a new bitmask term instance. */ EPR_SBmTerm* epr_create_bm_term(EPR_EBmOpCode op_code); /** * Creates a new bitmask reference term instance. */ EPR_SBmTerm* epr_create_bm_REF_term(char* ds_name, char* flag_name); /** * Creates a new bitmask NOT term instance. */ EPR_SBmTerm* epr_create_bm_NOT_term(EPR_SBmTerm* arg); /** * Creates a new bitmask OR term instance. */ EPR_SBmTerm* epr_create_bm_OR_term(EPR_SBmTerm* arg1, EPR_SBmTerm* arg2); /** * Creates a new bitmask reference AND term instance. */ EPR_SBmTerm* epr_create_bm_AND_term(EPR_SBmTerm* arg1, EPR_SBmTerm* arg2); /** * Releases a new bitmask term instance. */ void epr_free_bm_term(EPR_SBmTerm* term); /** * Creates a new bitmask expression from the given bitmask term. *
The expression returned is a valid in the sense that the epr_parse_bm_expr() * applied to the returned string would return an equivalent term. * * @param term the term to be converted */ char* epr_create_bm_expr(EPR_SBmTerm* term); /** * Prints the given term as an expression to the console. */ void epr_print_bm_term(EPR_SBmTerm* term); /** * Writes the given term as an expression to the given output stream. */ void epr_write_bm_term(EPR_SBmTerm* term, FILE* ostream); /** * Creates the coding flag info * * @param str the local path to dddb * * @return the the pointer at the coding flag information. */ EPR_SPtrArray* epr_create_flag_coding(EPR_SProductId* product_id, const char* str); /** * Creates the coding flag definition * * @return the the pointer at the coding flag definition information. */ EPR_SFlagDef* epr_create_flag_def(); /** * Releases the coding flag definition */ void epr_free_flag_def(EPR_SFlagDef* flag_def); /** * Releases the coding flag info */ void epr_free_flag_coding(EPR_SPtrArray* flag_coding); #ifdef __cplusplus } /* extern "C" */ #endif #endif /* #ifndef EPR_BITMASK_H_INCL */