Change-Id: I4d20e7537b1ee3b00fcaa42146b3f2681741074d
Signed-off-by: Romain Forlot <romain.forlot@iot.bzh>
#include "timer.h"
#include "openxc.pb.h"
#include "timer.h"
#include "openxc.pb.h"
typedef uint64_t (*SignalEncoder)(struct CanSignal* signal,
openxc_DynamicField* value, bool* send);
typedef uint64_t (*SignalEncoder)(struct CanSignal* signal,
openxc_DynamicField* value, bool* send);
+/* CanBus represent a can device definition get from configuraiton file */
+class CanBus {
+ private:
+ /* Got from conf file */
+ std::string deviceName;
+
+ int socket;
+ bool is_fdmode_on;
+ struct sockaddr_can txAddress;
+
+ public:
+ int open();
+ int close();
+};
+
/* Public: The ID format for a CAN message.
*
* STANDARD - standard 11-bit CAN arbitration ID.
/* Public: The ID format for a CAN message.
*
* STANDARD - standard 11-bit CAN arbitration ID.
* limitations under the License.
*/
* limitations under the License.
*/
-#define _GNU_SOURCE
-
-#include <string.h>
-#include <stdbool.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <net/if.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <net/if.h>
#include <linux/can.h>
#include <linux/can/raw.h>
#include <linux/can.h>
#include <linux/can/raw.h>
#include <fcntl.h>
#include <systemd/sd-event.h>
#include <errno.h>
#include <fcntl.h>
#include <systemd/sd-event.h>
#include <errno.h>
+#include <vector>
+#include <map>
+#include <queue>
+#include <string>
+#include <functional>
+#include <memory>
#include <json-c/json.h>
#include <openxc.pb.h>
#include <json-c/json.h>
#include <openxc.pb.h>
/*************************************************************************/
/*************************************************************************/
/*************************************************************************/
/*************************************************************************/
-/*
- * Retry a function 3 times
- *
- * param int function(): function that return an int wihtout any parameter
- *
- * return : 0 if ok, -1 if failed
- *
- */
-static int retry( int(*func)())
-{
- int i;
-
- for (i=0;i<4;i++)
- {
- if ( (*func)() >= 0)
- {
- return 0;
- }
- usleep(100000);
- }
- return -1;
-}
-
-/*
- * Test that socket is really opened
- *
- * param
- *
- * return : 0 or positive int if ok, negative value if failed
- *
- */
-static int socket_test()
-{
- if (can_handler.socket < 0)
- {
- return -1;
- }
- return 0;
-}
-
/*
* Browse chained list and return the one with specified id
*
/*
* Browse chained list and return the one with specified id
*
current = current->next;
}
current = current->next;
}
/** **/
/*************************************************************************/
/*************************************************************************/
/** **/
/*************************************************************************/
/*************************************************************************/
/*
* open the can socket
*/
/*
* open the can socket
*/
-static int open_can_dev()
{
const int canfd_on = 1;
struct ifreq ifr;
{
const int canfd_on = 1;
struct ifreq ifr;
- struct timeval timeout = {1,0};
+ struct timeval timeout = {1, 0};
- DEBUG(interface, "open_can_dev: CAN Handler socket : %d", can_handler.socket);
- if (can_handler.socket >= 0)
- close(can_handler.socket);
+ DEBUG(interface, "open_can_dev: CAN Handler socket : %d", socket);
+ if (socket >= 0)
+ close(socket);
- can_handler.socket = socket(PF_CAN, SOCK_RAW, CAN_RAW);
- if (can_handler.socket < 0)
+ socket = socket(PF_CAN, SOCK_RAW, CAN_RAW);
+ if (socket < 0)
{
ERROR(interface, "open_can_dev: socket could not be created");
}
else
{
/* Set timeout for read */
{
ERROR(interface, "open_can_dev: socket could not be created");
}
else
{
/* Set timeout for read */
- setsockopt(can_handler.socket, SOL_SOCKET, SO_RCVTIMEO, (char *)&timeout, sizeof(timeout));
+ setsockopt(socket, SOL_SOCKET, SO_RCVTIMEO, (char *)&timeout, sizeof(timeout));
/* try to switch the socket into CAN_FD mode */
/* try to switch the socket into CAN_FD mode */
- if (setsockopt(can_handler.socket, SOL_CAN_RAW, CAN_RAW_FD_FRAMES, &canfd_on, sizeof(canfd_on)) < 0)
+ if (setsockopt(socket, SOL_CAN_RAW, CAN_RAW_FD_FRAMES, &canfd_on, sizeof(canfd_on)) < 0)
{
NOTICE(interface, "open_can_dev: Can not switch into CAN Extended frame format.");
{
NOTICE(interface, "open_can_dev: Can not switch into CAN Extended frame format.");
- can_handler.is_fdmode_on = false;
- can_handler.is_fdmode_on = true;
}
/* Attempts to open a socket to CAN bus */
}
/* Attempts to open a socket to CAN bus */
- strcpy(ifr.ifr_name, can_handler.device);
- if(ioctl(can_handler.socket, SIOCGIFINDEX, &ifr) < 0)
+ strcpy(ifr.ifr_name, device);
+ if(ioctl(socket, SIOCGIFINDEX, &ifr) < 0)
ERROR(interface, "open_can_dev: ioctl failed");
else
{
ERROR(interface, "open_can_dev: ioctl failed");
else
{
- can_handler.txAddress.can_family = AF_CAN;
- can_handler.txAddress.can_ifindex = ifr.ifr_ifindex;
+ txAddress.can_family = AF_CAN;
+ txAddress.can_ifindex = ifr.ifr_ifindex;
/* And bind it to txAddress */
/* And bind it to txAddress */
- if (bind(can_handler.socket, (struct sockaddr *)&can_handler.txAddress, sizeof(can_handler.txAddress)) < 0)
+ if (bind(socket, (struct sockaddr *)&txAddress, sizeof(txAddress)) < 0)
{
ERROR(interface, "open_can_dev: bind failed");
}
else
{
{
ERROR(interface, "open_can_dev: bind failed");
}
else
{
- fcntl(can_handler.socket, F_SETFL, O_NONBLOCK);
+ fcntl(socket, F_SETFL, O_NONBLOCK);
- close(can_handler.socket);
- can_handler.socket = -1;
+ close(socket);
+ socket = -1;
- rc = can_handler.socket;
if (rc >= 0)
{
/*
* TODO change old hvac write can frame to generic on_event
*/
if (rc >= 0)
{
/*
* TODO change old hvac write can frame to generic on_event
*/
- nbytes = sendto(can_handler.socket, &canfd_frame, sizeof(struct canfd_frame), 0,
- (struct sockaddr*)&can_handler.txAddress, sizeof(can_handler.txAddress));
+ nbytes = sendto(socket, &canfd_frame, sizeof(struct canfd_frame), 0,
+ (struct sockaddr*)&txAddress, sizeof(txAddress));
if (nbytes < 0)
{
ERROR(interface, "write_can: Sending CAN frame failed.");
if (nbytes < 0)
{
ERROR(interface, "write_can: Sending CAN frame failed.");
else
{
ERROR(interface, "write_can: socket not initialized. Attempt to reopen can device socket.");
else
{
ERROR(interface, "write_can: socket not initialized. Attempt to reopen can device socket.");
buf[offset++] = hex_asc_upper[canfd_frame->len & 0xF];
buf[offset] = 0;
buf[offset++] = hex_asc_upper[canfd_frame->len & 0xF];
buf[offset] = 0;
/* Test that socket is really opened */
if ( socket_test() < 0)
{
/* Test that socket is really opened */
if ( socket_test() < 0)
{
- if (retry(open_can_dev) < 0)
+ if (open_can_dev() < 0)
{
ERROR(interface, "read_can: Socket unavailable");
return -1;
}
}
{
ERROR(interface, "read_can: Socket unavailable");
return -1;
}
}
- nbytes = read(can_handler.socket, &canfd_frame, CANFD_MTU);
+ nbytes = read(socket, &canfd_frame, CANFD_MTU);
if (nbytes == CANFD_MTU)
{
if (nbytes == CANFD_MTU)
{
else
{
if (errno == ENETDOWN)
else
{
if (errno == ENETDOWN)
- ERROR(interface, "read_can: %s interface down", can_handler.device);
+ ERROR(interface, "read_can: %s interface down", device);
ERROR(interface, "read_can: Error reading CAN bus");
return -2;
}
ERROR(interface, "read_can: Error reading CAN bus");
return -2;
}
*
* Return 0 or positive value on success. Else negative value for failure.
*/
*
* Return 0 or positive value on success. Else negative value for failure.
*/
-static int connect_to_event_loop()
+static int connect_to_event_loop(CanBus &CanBus_handler)
{
sd_event *event_loop;
sd_event_source *source;
int rc;
{
sd_event *event_loop;
sd_event_source *source;
int rc;
- if (can_handler.socket < 0)
+ if (CanBus_handler.socket < 0)
- return can_handler.socket;
+ return CanBus_handler.socket;
}
event_loop = afb_daemon_get_event_loop(interface->daemon);
}
event_loop = afb_daemon_get_event_loop(interface->daemon);
- rc = sd_event_add_io(event_loop, &source, can_handler.socket, EPOLLIN, on_event, NULL);
+ rc = sd_event_add_io(event_loop, &source, CanBus_handler.socket, EPOLLIN, on_event, NULL);
- close(can_handler.socket);
- ERROR(interface, "Can't connect CAN bus %s to the event loop", can_handler.device);
+ CanBus_handler.close();
+ ERROR(interface, "Can't connect CAN bus %s to the event loop", CanBus_handler.device);
- NOTICE(interface, "Connected CAN bus %s to the event loop", can_handler.device);
+ NOTICE(interface, "Connected CAN bus %s to the event loop", CanBus_handler.device);
int afbBindingV1ServiceInit(struct afb_service service)
{
int afbBindingV1ServiceInit(struct afb_service service)
{
+ /* Open JSON conf file */
+
- retry(open_can_dev);
- return connect_to_event_loop();
+ CanBus_handler.open();
+
+ return connect_to_event_loop(CanBus_handler);
/* CAN variable initialization */
struct canfd_frame canfd_frame;
/* CAN variable initialization */
struct canfd_frame canfd_frame;
int socket;
char *device;
bool is_fdmode_on;
int socket;
char *device;
bool is_fdmode_on;