49 #include "lwm2m-server.h" 54 #define LOG_MODULE "lwm2m-srv" 55 #define LOG_LEVEL LOG_LEVEL_LWM2M 57 #define MAX_COUNT LWM2M_SERVER_MAX_COUNT 59 static lwm2m_status_t lwm2m_callback(lwm2m_object_instance_t *
object,
60 lwm2m_context_t *ctx);
62 static lwm2m_object_instance_t *create_instance(uint16_t instance_id,
63 lwm2m_status_t *status);
64 static int delete_instance(uint16_t instance_id, lwm2m_status_t *status);
65 static lwm2m_object_instance_t *get_first(lwm2m_status_t *status);
66 static lwm2m_object_instance_t *get_next(lwm2m_object_instance_t *instance,
67 lwm2m_status_t *status);
68 static lwm2m_object_instance_t *get_by_id(uint16_t instance_id,
69 lwm2m_status_t *status);
71 static const lwm2m_resource_id_t resources[] = {
72 RO(LWM2M_SERVER_SHORT_SERVER_ID),
73 RW(LWM2M_SERVER_LIFETIME_ID),
74 EX(LWM2M_SERVER_REG_UPDATE_TRIGGER_ID)
77 static const lwm2m_object_impl_t impl = {
78 .object_id = LWM2M_OBJECT_SERVER_ID,
79 .get_first = get_first,
81 .get_by_id = get_by_id,
82 .create_instance = create_instance,
83 .delete_instance = delete_instance,
85 static lwm2m_object_t server_object = {
90 static lwm2m_server_t server_instances[MAX_COUNT];
92 static lwm2m_object_instance_t *
93 create_instance(uint16_t instance_id, lwm2m_status_t *status)
95 lwm2m_object_instance_t *instance;
98 instance = get_by_id(instance_id, NULL);
99 if(instance != NULL) {
102 *status = LWM2M_STATUS_OPERATION_NOT_ALLOWED;
107 for(i = 0; i < MAX_COUNT; i++) {
108 if(server_instances[i].instance.instance_id == LWM2M_OBJECT_INSTANCE_NONE) {
109 server_instances[i].instance.callback = lwm2m_callback;
110 server_instances[i].instance.object_id = LWM2M_OBJECT_SERVER_ID;
111 server_instances[i].instance.instance_id = instance_id;
112 server_instances[i].instance.resource_ids = resources;
113 server_instances[i].instance.resource_count =
114 sizeof(resources) /
sizeof(lwm2m_resource_id_t);
115 server_instances[i].server_id = 0;
116 server_instances[i].lifetime = 0;
117 list_add(server_list, &server_instances[i].instance);
120 *status = LWM2M_STATUS_OK;
123 return &server_instances[i].instance;
128 *status = LWM2M_STATUS_SERVICE_UNAVAILABLE;
135 delete_instance(uint16_t instance_id, lwm2m_status_t *status)
137 lwm2m_object_instance_t *instance;
140 *status = LWM2M_STATUS_OK;
143 if(instance_id == LWM2M_OBJECT_INSTANCE_NONE) {
145 while((instance =
list_pop(server_list)) != NULL) {
146 instance->instance_id = LWM2M_OBJECT_INSTANCE_NONE;
151 instance = get_by_id(instance_id, NULL);
152 if(instance != NULL) {
153 instance->instance_id = LWM2M_OBJECT_INSTANCE_NONE;
161 static lwm2m_object_instance_t *
162 get_first(lwm2m_status_t *status)
165 *status = LWM2M_STATUS_OK;
170 static lwm2m_object_instance_t *
171 get_next(lwm2m_object_instance_t *instance, lwm2m_status_t *status)
174 *status = LWM2M_STATUS_OK;
176 return instance == NULL ? NULL : instance->next;
179 static lwm2m_object_instance_t *
180 get_by_id(uint16_t instance_id, lwm2m_status_t *status)
182 lwm2m_object_instance_t *instance;
184 *status = LWM2M_STATUS_OK;
188 instance = instance->next) {
189 if(instance->instance_id == instance_id) {
196 static lwm2m_status_t
197 lwm2m_callback(lwm2m_object_instance_t *
object,
198 lwm2m_context_t *ctx)
201 lwm2m_server_t *server;
202 server = (lwm2m_server_t *)
object;
204 if(ctx->operation == LWM2M_OP_WRITE) {
205 LOG_DBG(
"Write to: %d\n", ctx->resource_id);
206 switch(ctx->resource_id) {
207 case LWM2M_SERVER_LIFETIME_ID:
208 lwm2m_object_read_int(ctx, ctx->inbuf->buffer, ctx->inbuf->size, &value);
209 server->lifetime = value;
212 }
else if(ctx->operation == LWM2M_OP_READ) {
213 switch(ctx->resource_id) {
214 case LWM2M_SERVER_SHORT_SERVER_ID:
215 lwm2m_object_write_int(ctx, server->server_id);
217 case LWM2M_SERVER_LIFETIME_ID:
218 lwm2m_object_write_int(ctx, server->lifetime);
221 }
else if(ctx->operation == LWM2M_OP_EXECUTE) {
222 switch(ctx->resource_id) {
223 case LWM2M_SERVER_REG_UPDATE_TRIGGER_ID:
224 lwm2m_rd_client_update_triggered();
228 return LWM2M_STATUS_NOT_IMPLEMENTED;
231 return LWM2M_STATUS_OK;
235 lwm2m_server_add(uint16_t instance_id, uint16_t server_id, uint32_t lifetime)
237 lwm2m_server_t *server;
242 server = (lwm2m_server_t *)server->instance.next) {
243 if(server->server_id == server_id) {
245 if(server->instance.instance_id != instance_id) {
247 LOG_DBG(
"non-matching instance id for server %u\n", server_id);
250 server->lifetime = lifetime;
252 }
else if(server->instance.instance_id == instance_id) {
254 LOG_DBG(
"non-matching server id for instance %u\n", instance_id);
259 for(i = 0; i < MAX_COUNT; i++) {
260 if(server_instances[i].instance.instance_id == LWM2M_OBJECT_INSTANCE_NONE) {
261 server_instances[i].instance.callback = lwm2m_callback;
262 server_instances[i].instance.object_id = LWM2M_OBJECT_SERVER_ID;
263 server_instances[i].instance.instance_id = instance_id;
264 server_instances[i].instance.resource_ids = resources;
265 server_instances[i].instance.resource_count =
266 sizeof(resources) /
sizeof(lwm2m_resource_id_t);
267 server_instances[i].server_id = server_id;
268 server_instances[i].lifetime = lifetime;
269 list_add(server_list, &server_instances[i].instance);
271 return &server_instances[i];
275 LOG_WARN(
"no space for more servers\n");
281 lwm2m_server_init(
void)
289 for(i = 0; i < MAX_COUNT; i++) {
290 server_instances[i].instance.instance_id = LWM2M_OBJECT_INSTANCE_NONE;
292 lwm2m_engine_add_generic_object(&server_object);
Header file for the LWM2M object API
Linked list manipulation routines.
void * list_head(list_t list)
Get a pointer to the first element of a list.
Header file for the Contiki OMA LWM2M Registration and Bootstrap Client.
void list_add(list_t list, void *item)
Add an item at the end of a list.
void list_init(list_t list)
Initialize a list.
#define LIST(name)
Declare a linked list.
Header file for the Contiki OMA LWM2M engine
void * list_pop(list_t list)
Remove the first object on a list.
void list_remove(list_t list, void *item)
Remove a specific element from a list.