summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorjfornal <jakub.fornal@intel.com>2016-09-02 14:04:57 +0200
committerGitHub <noreply@github.com>2016-09-02 14:04:57 +0200
commit10309b48d18740e11736be69d92e069450ac673b (patch)
tree22786fda76caddf56d825f1a83e7a3a357052bbd
parente880a5e652e6c88d5b0665ec209039a30781346a (diff)
parenta86a949a6ceef5ed884dba5bb18edf1d64a72d49 (diff)
downloadOpen-AVB-10309b48d18740e11736be69d92e069450ac673b.tar.gz
Merge pull request #1 from AVnu/open-avb-next
Merge of AVnu/Open-AVB/open-avb-next into jfornal/Open-AVB/open-avb-next
-rw-r--r--daemons/gptp/common/avbts_message.hpp6
-rw-r--r--daemons/gptp/common/ieee1588port.cpp9
-rw-r--r--daemons/gptp/linux/build/Makefile13
-rw-r--r--daemons/gptp/linux/src/daemon_cl.cpp9
-rw-r--r--daemons/gptp/linux/src/linux_hal_generic.cpp51
-rw-r--r--daemons/gptp/linux/src/linux_hal_generic.hpp3
-rw-r--r--daemons/mrpd/mrp.c1
-rw-r--r--kmod/igb/igb.h10
-rw-r--r--kmod/igb/igb_main.c304
-rw-r--r--lib/avtp_pipeline/platform/Linux/tl/openavb_tl_osal.c14
-rw-r--r--lib/avtp_pipeline/tl/openavb_talker.c2
11 files changed, 313 insertions, 109 deletions
diff --git a/daemons/gptp/common/avbts_message.hpp b/daemons/gptp/common/avbts_message.hpp
index 661e88c9..1e8220a1 100644
--- a/daemons/gptp/common/avbts_message.hpp
+++ b/daemons/gptp/common/avbts_message.hpp
@@ -1059,16 +1059,16 @@ class SignallingTLV {
*/
SignallingTLV() {
tlvType = PLAT_htons(0x3);
- lengthField = PLAT_htons(28);
+ lengthField = PLAT_htons(12);
organizationId[0] = '\x00';
organizationId[1] = '\x80';
organizationId[2] = '\xC2';
organizationSubType_ms = 0;
- organizationSubType_ls = PLAT_htons(1);
+ organizationSubType_ls = PLAT_htons(2);
linkDelayInterval = 0;
timeSyncInterval = 0;
announceInterval = 0;
- flags = 0;
+ flags = 3;
reserved = PLAT_htons(0);
}
diff --git a/daemons/gptp/common/ieee1588port.cpp b/daemons/gptp/common/ieee1588port.cpp
index dac87a75..34edf4d1 100644
--- a/daemons/gptp/common/ieee1588port.cpp
+++ b/daemons/gptp/common/ieee1588port.cpp
@@ -582,7 +582,7 @@ void IEEE1588Port::processEvent(Event e)
// Send an initial signalling message
PTPMessageSignalling *sigMsg = new PTPMessageSignalling(this);
if (sigMsg) {
- sigMsg->setintervals(log_min_mean_pdelay_req_interval, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoSend);
+ sigMsg->setintervals(PTPMessageSignalling::sigMsgInterval_NoSend, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoSend);
sigMsg->sendPort(this, NULL);
delete sigMsg;
}
@@ -732,7 +732,7 @@ void IEEE1588Port::processEvent(Event e)
// Send an initial signaling message
PTPMessageSignalling *sigMsg = new PTPMessageSignalling(this);
if (sigMsg) {
- sigMsg->setintervals(log_min_mean_pdelay_req_interval, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoSend);
+ sigMsg->setintervals(PTPMessageSignalling::sigMsgInterval_NoSend, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoSend);
sigMsg->sendPort(this, NULL);
delete sigMsg;
}
@@ -1202,7 +1202,10 @@ void IEEE1588Port::processEvent(Event e)
// Send operational signalling message
PTPMessageSignalling *sigMsg = new PTPMessageSignalling(this);
if (sigMsg) {
- sigMsg->setintervals(log_min_mean_pdelay_req_interval, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoChange);
+ if (automotive_profile)
+ sigMsg->setintervals(PTPMessageSignalling::sigMsgInterval_NoChange, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoChange);
+ else
+ sigMsg->setintervals(log_min_mean_pdelay_req_interval, log_mean_sync_interval, PTPMessageSignalling::sigMsgInterval_NoChange);
sigMsg->sendPort(this, NULL);
delete sigMsg;
}
diff --git a/daemons/gptp/linux/build/Makefile b/daemons/gptp/linux/build/Makefile
index 02d082f1..21048c06 100644
--- a/daemons/gptp/linux/build/Makefile
+++ b/daemons/gptp/linux/build/Makefile
@@ -33,6 +33,19 @@ ALTERNATE_LINUX_INCPATH=$(HOME)/header/include/
CFLAGS_G = -Wall -std=c++0x -g -I. -I../../common -I../src \
-I$(ALTERNATE_LINUX_INCPATH)
+# Check to see if PTP cross-timestamping is supported in hardware/driver
+# and, if so, add flag to compile in support
+
+PRECISE_TIME_TEST = "\#include <linux/ptp_clock.h>\\n\
+\#ifdef PTP_SYS_OFFSET_PRECISE\\nint main(){return 0;}\\n\#endif"
+
+HAS_PRECISE_TIME = $(shell echo $(PRECISE_TIME_TEST) | gcc -xc - \
+-I$(ALTERNATE_LINUX_INCPATH) -o /dev/null > /dev/null 2>&1 ; echo $$?)
+
+ifeq ($(HAS_PRECISE_TIME),0)
+ CFLAGS_G += -DPTP_HW_CROSSTSTAMP
+endif
+
CPPFLAGS_G = $(CFLAGS_G) -Wnon-virtual-dtor
LDFLAGS_G = -lpthread -lrt
diff --git a/daemons/gptp/linux/src/daemon_cl.cpp b/daemons/gptp/linux/src/daemon_cl.cpp
index 35282e9b..b5b46a10 100644
--- a/daemons/gptp/linux/src/daemon_cl.cpp
+++ b/daemons/gptp/linux/src/daemon_cl.cpp
@@ -363,10 +363,6 @@ int main(int argc, char **argv)
portInit.lock_factory = lock_factory;
pPort = new IEEE1588Port(&portInit);
- if (!pPort->init_port(phy_delay)) {
- printf("failed to initialize port \n");
- return -1;
- }
if(use_config_file)
{
@@ -408,6 +404,11 @@ int main(int argc, char **argv)
}
+ if (!pPort->init_port(phy_delay)) {
+ printf("failed to initialize port \n");
+ return -1;
+ }
+
if( restoredataptr != NULL ) {
if( !restorefailed ) {
restorefailed = !pPort->restoreSerializedState( restoredataptr, &restoredatacount );
diff --git a/daemons/gptp/linux/src/linux_hal_generic.cpp b/daemons/gptp/linux/src/linux_hal_generic.cpp
index b1dc2485..1dbcbc18 100644
--- a/daemons/gptp/linux/src/linux_hal_generic.cpp
+++ b/daemons/gptp/linux/src/linux_hal_generic.cpp
@@ -222,7 +222,9 @@ bool LinuxTimestamperGeneric::HWTimestamper_init
cross_stamp_good = false;
int phc_index;
char ptp_device[] = PTP_DEVICE;
-
+#ifdef PTP_HW_CROSSTSTAMP
+ struct ptp_clock_caps ptp_capability;
+#endif
_private = new LinuxTimestamperGenericPrivate;
pthread_mutex_init( &_private->cross_stamp_lock, NULL );
@@ -244,6 +246,16 @@ bool LinuxTimestamperGeneric::HWTimestamper_init
return false;
}
+#ifdef PTP_HW_CROSSTSTAMP
+ // Query PTP stack for availability of HW cross-timestamp
+ if( ioctl( phc_fd, PTP_CLOCK_GETCAPS, &ptp_capability ) == -1 )
+ {
+ GPTP_LOG_ERROR( "Failed to query PTP clock capabilities" );
+ return false;
+ }
+ precise_timestamp_enabled = ptp_capability.cross_timestamping;
+#endif
+
if( !resetFrequencyAdjustment() ) {
GPTP_LOG_ERROR( "Failed to reset (zero) frequency adjustment" );
return false;
@@ -411,20 +423,39 @@ static inline Timestamp pctTimestamp( struct ptp_clock_time *t ) {
return result;
}
+// Use HW cross-timestamp if available
bool LinuxTimestamperGeneric::HWTimestamper_gettime
( Timestamp *system_time, Timestamp *device_time, uint32_t *local_clock,
uint32_t *nominal_clock_rate ) {
- unsigned i;
- struct ptp_sys_offset offset;
- struct ptp_clock_time *pct;
- struct ptp_clock_time *system_time_l, *device_time_l;
+ if( phc_fd == -1 )
+ return false;
- int64_t interval = LLONG_MAX;
+#ifdef PTP_HW_CROSSTSTAMP
+ if( precise_timestamp_enabled )
+ {
+ struct ptp_sys_offset_precise offset;
+ memset( &offset, 0, sizeof(offset));
+ if( ioctl( phc_fd, PTP_SYS_OFFSET_PRECISE, &offset ) == 0 )
+ {
+ *device_time = pctTimestamp( &offset.device );
+ *system_time = pctTimestamp( &offset.sys_realtime );
+
+ return true;
+ }
+ }
+#endif
+
+ {
+ unsigned i;
+ struct ptp_clock_time *pct;
+ struct ptp_clock_time *system_time_l, *device_time_l;
+ int64_t interval = LLONG_MAX;
+ struct ptp_sys_offset offset;
- if( phc_fd != -1 ) {
memset( &offset, 0, sizeof(offset));
offset.n_samples = PTP_MAX_SAMPLES;
- ioctl( phc_fd, PTP_SYS_OFFSET, &offset );
+ if( ioctl( phc_fd, PTP_SYS_OFFSET, &offset ) == -1 )
+ return false;
pct = &offset.ts[0];
for( i = 0; i < offset.n_samples; ++i ) {
@@ -439,9 +470,7 @@ bool LinuxTimestamperGeneric::HWTimestamper_gettime
*device_time = pctTimestamp( device_time_l );
*system_time = pctTimestamp( system_time_l );
-
- return true;
}
- return false;
+ return true;
}
diff --git a/daemons/gptp/linux/src/linux_hal_generic.hpp b/daemons/gptp/linux/src/linux_hal_generic.hpp
index 5b33dad5..abe1f276 100644
--- a/daemons/gptp/linux/src/linux_hal_generic.hpp
+++ b/daemons/gptp/linux/src/linux_hal_generic.hpp
@@ -62,6 +62,9 @@ private:
bool cross_stamp_good;
std::list<Timestamp> rxTimestampList;
LinuxNetworkInterfaceList iface_list;
+#ifdef PTP_HW_CROSSTSTAMP
+ bool precise_timestamp_enabled;
+#endif
TicketingLock *net_lock;
diff --git a/daemons/mrpd/mrp.c b/daemons/mrpd/mrp.c
index 1537facf..3a162b37 100644
--- a/daemons/mrpd/mrp.c
+++ b/daemons/mrpd/mrp.c
@@ -665,7 +665,6 @@ int mrp_applicant_fsm(struct mrp_database *mrp_db,
optional = 1;
tx = 1;
sndmsg = MRP_SND_IN;
- mrp_state = MRP_VO_STATE;
break;
default:
break;
diff --git a/kmod/igb/igb.h b/kmod/igb/igb.h
index edd858b3..1da12050 100644
--- a/kmod/igb/igb.h
+++ b/kmod/igb/igb.h
@@ -575,7 +575,6 @@ struct igb_adapter {
/* OS defined structs */
struct pci_dev *pdev;
/* user-dma specific variables */
- struct igb_user_page *userpages;
u32 uring_tx_init;
u32 uring_rx_init;
#ifndef HAVE_NETDEV_STATS_IN_NETDEV
@@ -895,4 +894,13 @@ struct igb_link_cmd {
u32 duplex;
};
+struct igb_private_data {
+ struct igb_adapter *adapter;
+ /* user-dma specific variable for buffer */
+ struct igb_user_page *userpages;
+ /* user-dma specific variable for TX and RX */
+ u32 uring_tx_init;
+ u32 uring_rx_init;
+};
+
#endif /* _IGB_H_ */
diff --git a/kmod/igb/igb_main.c b/kmod/igb/igb_main.c
index f1534180..79dead8f 100644
--- a/kmod/igb/igb_main.c
+++ b/kmod/igb/igb_main.c
@@ -2686,7 +2686,6 @@ static int igb_probe(struct pci_dev *pdev,
adapter->msg_enable = (1 << debug) - 1;
/* AVB specific */
- adapter->userpages = NULL;
adapter->uring_tx_init = 0;
adapter->uring_rx_init = 0;
mutex_init(&adapter->lock);
@@ -10137,6 +10136,7 @@ static struct igb_adapter *igb_lookup(char *id)
static int igb_bind(struct file *file, void __user *argp)
{
+ struct igb_private_data *igb_priv = file->private_data;
struct igb_adapter *adapter;
struct igb_bind_cmd req;
int err = 0;
@@ -10146,13 +10146,18 @@ static int igb_bind(struct file *file, void __user *argp)
printk("bind to iface %s\n", req.iface);
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
adapter = igb_lookup(req.iface);
if (adapter == NULL) {
printk("lookup failed to iface %s\n", req.iface);
return -ENOENT;
}
- file->private_data = adapter;
+ igb_priv->adapter = adapter;
req.mmap_size = 0;
req.mmap_size = pci_resource_len(adapter->pdev, 0);
@@ -10166,30 +10171,41 @@ static int igb_bind(struct file *file, void __user *argp)
return 0;
failed:
- file->private_data = NULL;
+ igb_priv->adapter = NULL;
return err;
}
static int igb_unbind(struct file *file)
{
struct igb_adapter *adapter;
+ struct igb_private_data *igb_priv = file->private_data;
- adapter = file->private_data;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+ adapter = igb_priv->adapter;
if (adapter == NULL)
return -EBADFD;
- file->private_data = NULL;
+ igb_priv->adapter = NULL;
return 0;
}
static long igb_getspeed(struct file *file, void __user *arg)
{
+ struct igb_private_data *igb_priv = file->private_data;
struct igb_adapter *adapter;
struct igb_link_cmd req;
u32 link;
- adapter = file->private_data;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
+ adapter = igb_priv->adapter;
if (adapter == NULL) {
printk("map to unbound device!\n");
return -ENOENT;
@@ -10213,16 +10229,118 @@ static long igb_getspeed(struct file *file, void __user *arg)
return 0;
}
+static long igb_mapbuf_user(struct file *file, void __user *arg, int ring)
+{
+ struct igb_private_data *igb_priv = file->private_data;
+ struct igb_adapter *adapter;
+ struct igb_buf_cmd req;
+ int err = 0;
+ struct page *page;
+ dma_addr_t page_dma;
+ struct igb_user_page *userpage;
+
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
+ adapter = igb_priv->adapter;
+ if (adapter == NULL) {
+ printk("map to unbound device!\n");
+ return -ENOENT;
+ }
+
+ if (copy_from_user(&req, arg, sizeof(req)))
+ return -EFAULT;
+
+ userpage = vzalloc(sizeof(struct igb_user_page));
+ if (unlikely(!userpage)) {
+ err = -ENOMEM;
+ goto failed;
+ }
+
+ mutex_lock(&adapter->lock);
+ if (igb_priv->userpages == NULL) {
+ igb_priv->userpages = userpage;
+ } else {
+ userpage->next = igb_priv->userpages;
+ igb_priv->userpages->prev = userpage;
+ igb_priv->userpages = userpage;
+ }
+
+#if defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL)
+#if defined(CONFIG_ZONE_DMA32)
+ page = alloc_page(GFP_ATOMIC | __GFP_COLD | GFP_DMA32);
+#else /* defined(CONFIG_ZONE_DMA32) */
+ page = alloc_page(GFP_ATOMIC | __GFP_COLD | GFP_DMA);
+#endif /* defined(CONFIG_ZONE_DMA32) */
+#else /* defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL) */
+ page = alloc_page(GFP_ATOMIC | __GFP_COLD);
+#endif /* defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL) */
+ if (unlikely(!page)) {
+ err = -ENOMEM;
+ goto page_failed;
+ }
+
+ page_dma = dma_map_page(pci_dev_to_dev(adapter->pdev), page,
+ 0, PAGE_SIZE, DMA_FROM_DEVICE);
+
+ if (dma_mapping_error(pci_dev_to_dev(adapter->pdev), page_dma)) {
+ err = -ENOMEM;
+ goto map_failed;
+ }
+
+ igb_priv->userpages->page = page;
+ igb_priv->userpages->page_dma = page_dma;
+
+ req.physaddr = page_dma;
+ req.mmap_size = PAGE_SIZE;
+ mutex_unlock(&adapter->lock);
+
+ if (copy_to_user(arg, &req, sizeof(req))) {
+ printk("copyout to user failed\n");
+ err = -EFAULT;
+ mutex_lock(&adapter->lock);
+ goto copy_failed;
+ }
+
+ return 0;
+
+copy_failed:
+ dma_unmap_page(pci_dev_to_dev(adapter->pdev),
+ userpage->page_dma, PAGE_SIZE,
+ DMA_FROM_DEVICE);
+map_failed:
+ put_page(userpage->page);
+page_failed:
+ if (userpage->prev)
+ userpage->prev->next = userpage->next;
+ if (userpage->next)
+ userpage->next->prev = userpage->prev;
+ if (userpage == igb_priv->userpages)
+ igb_priv->userpages = userpage->next;
+ vfree(userpage);
+ mutex_unlock(&adapter->lock);
+failed:
+ return err;
+}
+
static long igb_mapbuf(struct file *file, void __user *arg, int ring)
{
+ struct igb_private_data *igb_priv = file->private_data;
struct igb_adapter *adapter;
struct igb_buf_cmd req;
int err = 0;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
if (copy_from_user(&req, arg, sizeof(req)))
return -EFAULT;
- adapter = file->private_data;
+ adapter = igb_priv->adapter;
if (adapter == NULL) {
printk("map to unbound device!\n");
return -ENOENT;
@@ -10235,15 +10353,19 @@ static long igb_mapbuf(struct file *file, void __user *arg, int ring)
return -EINVAL;
}
+ mutex_lock(&adapter->lock);
if (adapter->uring_tx_init & (1 << req.queue)) {
+ mutex_unlock(&adapter->lock);
printk("mapring:queue in use (%d)\n", req.queue);
return -EBUSY;
}
adapter->uring_tx_init |= (1 << req.queue);
+ igb_priv->uring_tx_init |= (1 << req.queue);
req.physaddr = adapter->tx_ring[req.queue]->dma;
req.mmap_size = adapter->tx_ring[req.queue]->size;
+ mutex_unlock(&adapter->lock);
} else if (ring == IGB_MAP_RX_RING) {
if (req.queue >= 3) {
printk("mapring:invalid queue specified(%d)\n",
@@ -10251,66 +10373,22 @@ static long igb_mapbuf(struct file *file, void __user *arg, int ring)
return -EINVAL;
}
+ mutex_lock(&adapter->lock);
if (adapter->uring_rx_init & (1 << req.queue)) {
+ mutex_unlock(&adapter->lock);
printk("mapring:queue in use (%d)\n", req.queue);
return -EBUSY;
}
adapter->uring_rx_init |= (1 << req.queue);
+ igb_priv->uring_rx_init |= (1 << req.queue);
req.physaddr = adapter->rx_ring[req.queue]->dma;
req.mmap_size = adapter->rx_ring[req.queue]->size;
- } else {
- struct page *page;
- dma_addr_t page_dma;
- struct igb_user_page *userpage;
-
- userpage = vzalloc(sizeof(struct igb_user_page));
- if (unlikely(!userpage)) {
- err = -ENOMEM;
- goto failed;
- }
-
- mutex_lock(&adapter->lock);
- if (adapter->userpages == NULL) {
- adapter->userpages = userpage;
- } else {
- userpage->next = adapter->userpages;
- adapter->userpages->prev = userpage;
- adapter->userpages = userpage;
- }
-
-#if defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL)
-#if defined(CONFIG_ZONE_DMA32)
- page = alloc_page(GFP_ATOMIC | __GFP_COLD | GFP_DMA32);
-#else /* defined(CONFIG_ZONE_DMA32) */
- page = alloc_page(GFP_ATOMIC | __GFP_COLD | GFP_DMA);
-#endif /* defined(CONFIG_ZONE_DMA32) */
-#else /* defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL) */
- page = alloc_page(GFP_ATOMIC | __GFP_COLD);
-#endif /* defined(CONFIG_IGB_SUPPORT_32BIT_IOCTL) */
- if (unlikely(!page)) {
- err = -ENOMEM;
- mutex_unlock(&adapter->lock);
- goto failed;
- }
-
- page_dma = dma_map_page(pci_dev_to_dev(adapter->pdev), page,
- 0, PAGE_SIZE, DMA_FROM_DEVICE);
-
- if (dma_mapping_error(pci_dev_to_dev(adapter->pdev), page_dma)) {
- put_page(page);
- err = -ENOMEM;
- mutex_unlock(&adapter->lock);
- goto failed;;
- }
-
- adapter->userpages->page = page;
- adapter->userpages->page_dma = page_dma;
-
- req.physaddr = page_dma;
- req.mmap_size = PAGE_SIZE;
mutex_unlock(&adapter->lock);
+ } else {
+ printk("mapring: invalid ioctl %d\n", _IOC_NR(ring));
+ return -EINVAL;
}
if (copy_to_user(arg, &req, sizeof(req))) {
@@ -10328,13 +10406,19 @@ failed:
static long igb_unmapbuf(struct file *file, void __user *arg, int ring)
{
int err = 0;
+ struct igb_private_data *igb_priv = file->private_data;
struct igb_adapter *adapter;
struct igb_buf_cmd req;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
if (copy_from_user(&req, arg, sizeof(req)))
return -EFAULT;
- adapter = file->private_data;
+ adapter = igb_priv->adapter;
if (adapter == NULL) {
printk("map to unbound device!\n");
return -ENOENT;
@@ -10345,25 +10429,43 @@ static long igb_unmapbuf(struct file *file, void __user *arg, int ring)
if (req.queue >= 3)
return -EINVAL;
- if (0 == (adapter->uring_tx_init & (1 << req.queue)))
+ mutex_lock(&adapter->lock);
+ if (0 == (igb_priv->uring_tx_init & (1 << req.queue))) {
+ mutex_unlock(&adapter->lock);
return -EINVAL;
+ } else {
+ if (0 == (adapter->uring_tx_init & (1 << req.queue))) {
+ printk("Warning: invalid tx ring buffer state!\n");
+ }
+ }
adapter->uring_tx_init &= ~(1 << req.queue);
+ igb_priv->uring_tx_init &= ~(1 << req.queue);
+ mutex_unlock(&adapter->lock);
} else if (ring == IGB_UNMAP_RX_RING) {
/* its easy to figure out what to free on the rings ... */
if (req.queue >= 3)
return -EINVAL;
- if (0 == (adapter->uring_rx_init & (1 << req.queue)))
+ mutex_lock(&adapter->lock);
+ if (0 == (igb_priv->uring_rx_init & (1 << req.queue))) {
+ mutex_unlock(&adapter->lock);
return -EINVAL;
+ } else {
+ if (0 == (adapter->uring_rx_init & (1 << req.queue))) {
+ printk("Warning: invalid rx ring buffer state!\n");
+ }
+ }
adapter->uring_rx_init &= ~(1 << req.queue);
+ igb_priv->uring_rx_init &= ~(1 << req.queue);
+ mutex_unlock(&adapter->lock);
} else {
/* have to find the corresponding page to free */
- struct igb_user_page *userpage;
+ struct igb_user_page *userpage;
mutex_lock(&adapter->lock);
- userpage = adapter->userpages;
+ userpage = igb_priv->userpages;
while (userpage != NULL) {
if (req.physaddr == userpage->page_dma)
@@ -10390,8 +10492,8 @@ static long igb_unmapbuf(struct file *file, void __user *arg, int ring)
if (userpage->next)
userpage->next->prev = userpage->prev;
- if (userpage == adapter->userpages)
- adapter->userpages = userpage->next;
+ if (userpage == igb_priv->userpages)
+ igb_priv->userpages = userpage->next;
vfree(userpage);
mutex_unlock(&adapter->lock);
@@ -10414,9 +10516,11 @@ static long igb_ioctl_file(struct file *file, unsigned int cmd,
break;
case IGB_MAP_TX_RING:
case IGB_MAP_RX_RING:
- case IGB_MAPBUF:
err = igb_mapbuf(file, argp, cmd);
break;
+ case IGB_MAPBUF:
+ err = igb_mapbuf_user(file, argp, cmd);
+ break;
case IGB_UNMAP_TX_RING:
case IGB_UNMAP_RX_RING:
case IGB_UNMAPBUF:
@@ -10435,37 +10539,67 @@ static long igb_ioctl_file(struct file *file, unsigned int cmd,
static int igb_open_file(struct inode *inode, struct file *file)
{
- file->private_data = NULL;
- return 0;
+ struct igb_private_data *igb_priv = NULL;
+ int ret = 0;
+
+ igb_priv = kzalloc(sizeof(struct igb_private_data *), GFP_KERNEL);
+ if (igb_priv == NULL) {
+ ret = -ENOMEM;
+ goto out;
+ }
+ igb_priv->uring_tx_init = 0;
+ igb_priv->uring_rx_init = 0;
+ igb_priv->userpages = NULL;
+ igb_priv->adapter = NULL;
+out:
+ file->private_data = igb_priv;
+ return ret;
}
static int igb_close_file(struct inode *inode, struct file *file)
{
- struct igb_adapter *adapter = file->private_data;
- int err;
+ struct igb_private_data *igb_priv = file->private_data;
+ struct igb_adapter *adapter = NULL;
+ int err = 0;
int i;
struct igb_user_page *userpage;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
+ adapter = igb_priv->adapter;
if (adapter == NULL)
- return 0;
+ goto out;
+ mutex_lock(&adapter->lock);
/* free up any rings and user-mapped pages */
for (i = 0; i < 3; i++) {
- if (adapter->uring_tx_init & (1 << i)) {
- igb_free_tx_resources(adapter->tx_ring[i]);
+ if (igb_priv->uring_tx_init & (1 << i)) {
+ if (adapter->uring_tx_init & (1 << i)) {
+ igb_free_tx_resources(adapter->tx_ring[i]);
+ } else {
+ printk("Warning: invalid tx ring buffer state!\n");
+ }
adapter->uring_tx_init &= ~(1 << i);
+ igb_priv->uring_tx_init &= ~(1 << i);
}
}
for (i = 0; i < 3; i++) {
- if (adapter->uring_rx_init & (1 << i)) {
- igb_free_rx_resources(adapter->rx_ring[i]);
+ if (igb_priv->uring_rx_init & (1 << i)) {
+ if (adapter->uring_rx_init & (1 << i)) {
+ igb_free_rx_resources(adapter->rx_ring[i]);
+ } else {
+ printk("Warning: invalid rx ring buffer state!\n");
+ }
adapter->uring_rx_init &= ~(1 << i);
+ igb_priv->uring_rx_init &= ~(1 << i);
}
}
- mutex_lock(&adapter->lock);
- userpage = adapter->userpages;
+ userpage = igb_priv->userpages;
while (userpage != NULL) {
dma_unmap_page(pci_dev_to_dev(adapter->pdev),
@@ -10482,15 +10616,18 @@ static int igb_close_file(struct inode *inode, struct file *file)
if (userpage->next)
userpage->next->prev = userpage->prev;
- if (userpage == adapter->userpages)
- adapter->userpages = userpage->next;
+ if (userpage == igb_priv->userpages)
+ igb_priv->userpages = userpage->next;
vfree(userpage);
- userpage = adapter->userpages;
+ userpage = igb_priv->userpages;
}
mutex_unlock(&adapter->lock);
err = igb_unbind(file);
+out:
+ file->private_data = NULL;
+ kfree(igb_priv);
return err;
}
@@ -10509,11 +10646,18 @@ static int igb_vm_fault(struct vm_area_struct *area, struct vm_fault *fdata)
static int igb_mmap(struct file *file, struct vm_area_struct *vma)
{
- struct igb_adapter *adapter = file->private_data;
+ struct igb_private_data *igb_priv = file->private_data;
+ struct igb_adapter *adapter = NULL;
unsigned long size = vma->vm_end - vma->vm_start;
dma_addr_t pgoff = vma->vm_pgoff;
dma_addr_t physaddr;
+ if (igb_priv == NULL) {
+ printk("cannot find private data!\n");
+ return -ENOENT;
+ }
+
+ adapter = igb_priv->adapter;
if (adapter == NULL)
return -ENODEV;
diff --git a/lib/avtp_pipeline/platform/Linux/tl/openavb_tl_osal.c b/lib/avtp_pipeline/platform/Linux/tl/openavb_tl_osal.c
index d6ca4264..d10ab6b8 100644
--- a/lib/avtp_pipeline/platform/Linux/tl/openavb_tl_osal.c
+++ b/lib/avtp_pipeline/platform/Linux/tl/openavb_tl_osal.c
@@ -297,11 +297,8 @@ static int openavbTLCfgCallback(void *user, const char *tlSection, const char *n
}
}
else if (MATCH(name, "ifname")) {
- if_info_t ifinfo;
- if (openavbCheckInterface(value, &ifinfo)) {
- strncpy(pCfg->ifname, value, IFNAMSIZ - 1);
- valOK = TRUE;
- }
+ strncpy(pCfg->ifname, value, IFNAMSIZ - 1);
+ valOK = TRUE;
}
else if (MATCH(name, "vlan_id")) {
errno = 0;
@@ -405,6 +402,13 @@ EXTERN_DLL_EXPORT bool openavbTLReadIniFileOsal(tl_handle_t TLhandle, const char
parseIniData.pNVCfg = pNVCfg;
int result = ini_parse(fileName, openavbTLCfgCallback, &parseIniData);
+ if (result == 0) {
+ if_info_t ifinfo;
+ if (!openavbCheckInterface(&parseIniData.pCfg->ifname, &ifinfo)) {
+ AVB_LOGF_ERROR("Invalid value: name=%s, value=%s", "ifname", parseIniData.pCfg->ifname);
+ return FALSE;
+ }
+ }
if (result < 0) {
AVB_LOGF_ERROR("Couldn't parse INI file: %s", fileName);
return FALSE;
diff --git a/lib/avtp_pipeline/tl/openavb_talker.c b/lib/avtp_pipeline/tl/openavb_talker.c
index 8bc6ca42..ed623a26 100644
--- a/lib/avtp_pipeline/tl/openavb_talker.c
+++ b/lib/avtp_pipeline/tl/openavb_talker.c
@@ -170,7 +170,7 @@ void talkerStopStream(tl_state_t *pTLState)
openavbTalkerGetStat(pTLState, TL_STAT_TX_FRAMES),
openavbTalkerGetStat(pTLState, TL_STAT_TX_LATE),
openavbTalkerGetStat(pTLState, TL_STAT_TX_BYTES),
- openavbRawsockGetTXOutOfBuffers(rawsock)
+ rawsock ? openavbRawsockGetTXOutOfBuffers(rawsock) : 0
);
if (pTLState->bStreaming) {