Kenji Arai / mbed-os_TYBLE16

Dependents:   TYBLE16_simple_data_logger TYBLE16_MP3_Air

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers lwip_snmp_mib2_system.c Source File

lwip_snmp_mib2_system.c

Go to the documentation of this file.
00001 /**
00002  * @file
00003  * Management Information Base II (RFC1213) SYSTEM objects and functions.
00004  */
00005 
00006 /*
00007  * Copyright (c) 2006 Axon Digital Design B.V., The Netherlands.
00008  * All rights reserved.
00009  *
00010  * Redistribution and use in source and binary forms, with or without modification,
00011  * are permitted provided that the following conditions are met:
00012  *
00013  * 1. Redistributions of source code must retain the above copyright notice,
00014  *    this list of conditions and the following disclaimer.
00015  * 2. Redistributions in binary form must reproduce the above copyright notice,
00016  *    this list of conditions and the following disclaimer in the documentation
00017  *    and/or other materials provided with the distribution.
00018  * 3. The name of the author may not be used to endorse or promote products
00019  *    derived from this software without specific prior written permission.
00020  *
00021  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
00022  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
00023  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
00024  * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00025  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
00026  * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00027  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00028  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
00029  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
00030  * OF SUCH DAMAGE.
00031  *
00032  * Author: Dirk Ziegelmeier <dziegel@gmx.de>
00033  *         Christiaan Simons <christiaan.simons@axon.tv>
00034  */
00035 
00036 #include "lwip/snmp.h"
00037 #include "lwip/apps/snmp.h"
00038 #include "lwip/apps/snmp_core.h"
00039 #include "lwip/apps/snmp_mib2.h"
00040 #include "lwip/apps/snmp_table.h"
00041 #include "lwip/apps/snmp_scalar.h"
00042 #include "lwip/sys.h"
00043 
00044 #include <string.h>
00045 
00046 #if LWIP_SNMP && SNMP_LWIP_MIB2
00047 
00048 #if SNMP_USE_NETCONN
00049 #define SYNC_NODE_NAME(node_name) node_name ## _synced
00050 #define CREATE_LWIP_SYNC_NODE(oid, node_name) \
00051    static const struct snmp_threadsync_node node_name ## _synced = SNMP_CREATE_THREAD_SYNC_NODE(oid, &node_name.node, &snmp_mib2_lwip_locks);
00052 #else
00053 #define SYNC_NODE_NAME(node_name) node_name
00054 #define CREATE_LWIP_SYNC_NODE(oid, node_name)
00055 #endif
00056 
00057 /* --- system .1.3.6.1.2.1.1 ----------------------------------------------------- */
00058 
00059 /** mib-2.system.sysDescr */
00060 static const u8_t   sysdescr_default[] = SNMP_LWIP_MIB2_SYSDESC;
00061 static const u8_t  *sysdescr           = sysdescr_default;
00062 static const u16_t *sysdescr_len       = NULL; /* use strlen for determining len */
00063 
00064 /** mib-2.system.sysContact */
00065 static const u8_t   syscontact_default[]     = SNMP_LWIP_MIB2_SYSCONTACT;
00066 static const u8_t  *syscontact               = syscontact_default;
00067 static const u16_t *syscontact_len           = NULL; /* use strlen for determining len */
00068 static u8_t        *syscontact_wr            = NULL; /* if writable, points to the same buffer as syscontact (required for correct constness) */
00069 static u16_t       *syscontact_wr_len        = NULL; /* if writable, points to the same buffer as syscontact_len (required for correct constness) */
00070 static u16_t        syscontact_bufsize       = 0;    /* 0=not writable */
00071 
00072 /** mib-2.system.sysName */
00073 static const u8_t   sysname_default[]        = SNMP_LWIP_MIB2_SYSNAME;
00074 static const u8_t  *sysname                  = sysname_default;
00075 static const u16_t *sysname_len              = NULL; /* use strlen for determining len */
00076 static u8_t        *sysname_wr               = NULL; /* if writable, points to the same buffer as sysname (required for correct constness) */
00077 static u16_t       *sysname_wr_len           = NULL; /* if writable, points to the same buffer as sysname_len (required for correct constness) */
00078 static u16_t        sysname_bufsize          = 0;    /* 0=not writable */
00079 
00080 /** mib-2.system.sysLocation */
00081 static const u8_t   syslocation_default[]    = SNMP_LWIP_MIB2_SYSLOCATION;
00082 static const u8_t  *syslocation              = syslocation_default;
00083 static const u16_t *syslocation_len           = NULL; /* use strlen for determining len */
00084 static u8_t        *syslocation_wr            = NULL; /* if writable, points to the same buffer as syslocation (required for correct constness) */
00085 static u16_t       *syslocation_wr_len        = NULL; /* if writable, points to the same buffer as syslocation_len (required for correct constness) */
00086 static u16_t        syslocation_bufsize       = 0;    /* 0=not writable */
00087 
00088 /**
00089  * @ingroup snmp_mib2
00090  * Initializes sysDescr pointers.
00091  *
00092  * @param str if non-NULL then copy str pointer
00093  * @param len points to string length, excluding zero terminator
00094  */
00095 void
00096 snmp_mib2_set_sysdescr(const u8_t *str, const u16_t *len)
00097 {
00098   if (str != NULL) {
00099     sysdescr     = str;
00100     sysdescr_len = len;
00101   }
00102 }
00103 
00104 /**
00105  * @ingroup snmp_mib2
00106  * Initializes sysContact pointers
00107  *
00108  * @param ocstr if non-NULL then copy str pointer
00109  * @param ocstrlen points to string length, excluding zero terminator.
00110  *        if set to NULL it is assumed that ocstr is NULL-terminated.
00111  * @param bufsize size of the buffer in bytes.
00112  *        (this is required because the buffer can be overwritten by snmp-set)
00113  *        if ocstrlen is NULL buffer needs space for terminating 0 byte.
00114  *        otherwise complete buffer is used for string.
00115  *        if bufsize is set to 0, the value is regarded as read-only.
00116  */
00117 void
00118 snmp_mib2_set_syscontact(u8_t *ocstr, u16_t *ocstrlen, u16_t bufsize)
00119 {
00120   if (ocstr != NULL) {
00121     syscontact         = ocstr;
00122     syscontact_wr      = ocstr;
00123     syscontact_len     = ocstrlen;
00124     syscontact_wr_len  = ocstrlen;
00125     syscontact_bufsize = bufsize;
00126   }
00127 }
00128 
00129 /**
00130  * @ingroup snmp_mib2
00131  * see \ref snmp_mib2_set_syscontact but set pointer to readonly memory
00132  */
00133 void
00134 snmp_mib2_set_syscontact_readonly(const u8_t *ocstr, const u16_t *ocstrlen)
00135 {
00136   if (ocstr != NULL) {
00137     syscontact         = ocstr;
00138     syscontact_len     = ocstrlen;
00139     syscontact_wr      = NULL;
00140     syscontact_wr_len  = NULL;
00141     syscontact_bufsize = 0;
00142   }
00143 }
00144 
00145 
00146 /**
00147  * @ingroup snmp_mib2
00148  * Initializes sysName pointers
00149  *
00150  * @param ocstr if non-NULL then copy str pointer
00151  * @param ocstrlen points to string length, excluding zero terminator.
00152  *        if set to NULL it is assumed that ocstr is NULL-terminated.
00153  * @param bufsize size of the buffer in bytes.
00154  *        (this is required because the buffer can be overwritten by snmp-set)
00155  *        if ocstrlen is NULL buffer needs space for terminating 0 byte.
00156  *        otherwise complete buffer is used for string.
00157  *        if bufsize is set to 0, the value is regarded as read-only.
00158  */
00159 void
00160 snmp_mib2_set_sysname(u8_t *ocstr, u16_t *ocstrlen, u16_t bufsize)
00161 {
00162   if (ocstr != NULL) {
00163     sysname         = ocstr;
00164     sysname_wr      = ocstr;
00165     sysname_len     = ocstrlen;
00166     sysname_wr_len  = ocstrlen;
00167     sysname_bufsize = bufsize;
00168   }
00169 }
00170 
00171 /**
00172  * @ingroup snmp_mib2
00173  * see \ref snmp_mib2_set_sysname but set pointer to readonly memory
00174  */
00175 void
00176 snmp_mib2_set_sysname_readonly(const u8_t *ocstr, const u16_t *ocstrlen)
00177 {
00178   if (ocstr != NULL) {
00179     sysname         = ocstr;
00180     sysname_len     = ocstrlen;
00181     sysname_wr      = NULL;
00182     sysname_wr_len  = NULL;
00183     sysname_bufsize = 0;
00184   }
00185 }
00186 
00187 /**
00188  * @ingroup snmp_mib2
00189  * Initializes sysLocation pointers
00190  *
00191  * @param ocstr if non-NULL then copy str pointer
00192  * @param ocstrlen points to string length, excluding zero terminator.
00193  *        if set to NULL it is assumed that ocstr is NULL-terminated.
00194  * @param bufsize size of the buffer in bytes.
00195  *        (this is required because the buffer can be overwritten by snmp-set)
00196  *        if ocstrlen is NULL buffer needs space for terminating 0 byte.
00197  *        otherwise complete buffer is used for string.
00198  *        if bufsize is set to 0, the value is regarded as read-only.
00199  */
00200 void
00201 snmp_mib2_set_syslocation(u8_t *ocstr, u16_t *ocstrlen, u16_t bufsize)
00202 {
00203   if (ocstr != NULL) {
00204     syslocation         = ocstr;
00205     syslocation_wr      = ocstr;
00206     syslocation_len     = ocstrlen;
00207     syslocation_wr_len  = ocstrlen;
00208     syslocation_bufsize = bufsize;
00209   }
00210 }
00211 
00212 /**
00213  * @ingroup snmp_mib2
00214  * see \ref snmp_mib2_set_syslocation but set pointer to readonly memory
00215  */
00216 void
00217 snmp_mib2_set_syslocation_readonly(const u8_t *ocstr, const u16_t *ocstrlen)
00218 {
00219   if (ocstr != NULL) {
00220     syslocation         = ocstr;
00221     syslocation_len     = ocstrlen;
00222     syslocation_wr      = NULL;
00223     syslocation_wr_len  = NULL;
00224     syslocation_bufsize = 0;
00225   }
00226 }
00227 
00228 
00229 static s16_t
00230 system_get_value(const struct snmp_scalar_array_node_def *node, void *value)
00231 {
00232   const u8_t  *var = NULL;
00233   const s16_t *var_len;
00234   u16_t result;
00235 
00236   switch (node->oid) {
00237     case 1: /* sysDescr */
00238       var     = sysdescr;
00239       var_len = (const s16_t *)sysdescr_len;
00240       break;
00241     case 2: { /* sysObjectID */
00242       const struct snmp_obj_id *dev_enterprise_oid = snmp_get_device_enterprise_oid();
00243       MEMCPY(value, dev_enterprise_oid->id, dev_enterprise_oid->len * sizeof(u32_t));
00244       return dev_enterprise_oid->len * sizeof(u32_t);
00245     }
00246     case 3: /* sysUpTime */
00247       MIB2_COPY_SYSUPTIME_TO((u32_t *)value);
00248       return sizeof(u32_t);
00249     case 4: /* sysContact */
00250       var     = syscontact;
00251       var_len = (const s16_t *)syscontact_len;
00252       break;
00253     case 5: /* sysName */
00254       var     = sysname;
00255       var_len = (const s16_t *)sysname_len;
00256       break;
00257     case 6: /* sysLocation */
00258       var     = syslocation;
00259       var_len = (const s16_t *)syslocation_len;
00260       break;
00261     case 7: /* sysServices */
00262       *(s32_t *)value = SNMP_SYSSERVICES;
00263       return sizeof(s32_t);
00264     default:
00265       LWIP_DEBUGF(SNMP_MIB_DEBUG, ("system_get_value(): unknown id: %"S32_F"\n", node->oid));
00266       return 0;
00267   }
00268 
00269   /* handle string values (OID 1,4,5 and 6) */
00270   LWIP_ASSERT("", (value != NULL));
00271   if (var_len == NULL) {
00272     result = (s16_t)strlen((const char *)var);
00273   } else {
00274     result = *var_len;
00275   }
00276   MEMCPY(value, var, result);
00277   return result;
00278 }
00279 
00280 static snmp_err_t
00281 system_set_test(const struct snmp_scalar_array_node_def *node, u16_t len, void *value)
00282 {
00283   snmp_err_t ret = SNMP_ERR_WRONGVALUE;
00284   const u16_t *var_bufsize  = NULL;
00285   const u16_t *var_wr_len;
00286 
00287   LWIP_UNUSED_ARG(value);
00288 
00289   switch (node->oid) {
00290     case 4: /* sysContact */
00291       var_bufsize  = &syscontact_bufsize;
00292       var_wr_len   = syscontact_wr_len;
00293       break;
00294     case 5: /* sysName */
00295       var_bufsize  = &sysname_bufsize;
00296       var_wr_len   = sysname_wr_len;
00297       break;
00298     case 6: /* sysLocation */
00299       var_bufsize  = &syslocation_bufsize;
00300       var_wr_len   = syslocation_wr_len;
00301       break;
00302     default:
00303       LWIP_DEBUGF(SNMP_MIB_DEBUG, ("system_set_test(): unknown id: %"S32_F"\n", node->oid));
00304       return ret;
00305   }
00306 
00307   /* check if value is writable at all */
00308   if (*var_bufsize > 0) {
00309     if (var_wr_len == NULL) {
00310       /* we have to take the terminating 0 into account */
00311       if (len < *var_bufsize) {
00312         ret = SNMP_ERR_NOERROR;
00313       }
00314     } else {
00315       if (len <= *var_bufsize) {
00316         ret = SNMP_ERR_NOERROR;
00317       }
00318     }
00319   } else {
00320     ret = SNMP_ERR_NOTWRITABLE;
00321   }
00322 
00323   return ret;
00324 }
00325 
00326 static snmp_err_t
00327 system_set_value(const struct snmp_scalar_array_node_def *node, u16_t len, void *value)
00328 {
00329   u8_t  *var_wr = NULL;
00330   u16_t *var_wr_len;
00331 
00332   switch (node->oid) {
00333     case 4: /* sysContact */
00334       var_wr     = syscontact_wr;
00335       var_wr_len = syscontact_wr_len;
00336       break;
00337     case 5: /* sysName */
00338       var_wr     = sysname_wr;
00339       var_wr_len = sysname_wr_len;
00340       break;
00341     case 6: /* sysLocation */
00342       var_wr     = syslocation_wr;
00343       var_wr_len = syslocation_wr_len;
00344       break;
00345     default:
00346       LWIP_DEBUGF(SNMP_MIB_DEBUG, ("system_set_value(): unknown id: %"S32_F"\n", node->oid));
00347       return SNMP_ERR_GENERROR;
00348   }
00349 
00350   /* no need to check size of target buffer, this was already done in set_test method */
00351   LWIP_ASSERT("", var_wr != NULL);
00352   MEMCPY(var_wr, value, len);
00353 
00354   if (var_wr_len == NULL) {
00355     /* add terminating 0 */
00356     var_wr[len] = 0;
00357   } else {
00358     *var_wr_len = len;
00359   }
00360 
00361   return SNMP_ERR_NOERROR;
00362 }
00363 
00364 static const struct snmp_scalar_array_node_def system_nodes[] = {
00365   {1, SNMP_ASN1_TYPE_OCTET_STRING, SNMP_NODE_INSTANCE_READ_ONLY},  /* sysDescr */
00366   {2, SNMP_ASN1_TYPE_OBJECT_ID,    SNMP_NODE_INSTANCE_READ_ONLY},  /* sysObjectID */
00367   {3, SNMP_ASN1_TYPE_TIMETICKS,    SNMP_NODE_INSTANCE_READ_ONLY},  /* sysUpTime */
00368   {4, SNMP_ASN1_TYPE_OCTET_STRING, SNMP_NODE_INSTANCE_READ_WRITE}, /* sysContact */
00369   {5, SNMP_ASN1_TYPE_OCTET_STRING, SNMP_NODE_INSTANCE_READ_WRITE}, /* sysName */
00370   {6, SNMP_ASN1_TYPE_OCTET_STRING, SNMP_NODE_INSTANCE_READ_WRITE}, /* sysLocation */
00371   {7, SNMP_ASN1_TYPE_INTEGER,      SNMP_NODE_INSTANCE_READ_ONLY}   /* sysServices */
00372 };
00373 
00374 const struct snmp_scalar_array_node snmp_mib2_system_node = SNMP_SCALAR_CREATE_ARRAY_NODE(1, system_nodes, system_get_value, system_set_test, system_set_value);
00375 
00376 #endif /* LWIP_SNMP && SNMP_LWIP_MIB2 */