Quantcast
Channel: Active questions tagged linux-kernel - Stack Overflow
Viewing all 12198 articles
Browse latest View live

Assembly function (crc_t10dif_pcl) varies in performance between different kernels

$
0
0

I do see a difference in the performance of the assembly function crc_t10dif_pcl between two difference kernels, one is 5.1.20 and the newer one in 5.5.6.

Here is the function in:

Now, I do not see the any significant difference between the two.

But I see that in v5.1.20 it finishes in ~400 microseconds, and in ~100 microseconds in v5.5.6.

This is on an AMD EPYC 7351 16-Core Processor for both cases.

I am not sure where is that coming from?

Is there a cpu feature that could explain this? or something else?


Why there was a lot of FIN retransmission(TCP/IP)?

$
0
0
  21088 2020-03-02 21:59:27.815879    10.9.180.89           161.117.97.14         TCP      76     41818 → 80 [SYN] Seq=0 Win=65535 Len=0 MSS=1370 SACK_PERM=1 TSval=1656722322 TSecr=0 WS=512
  21092 2020-03-02 21:59:27.903661    161.117.97.14         10.9.180.89           TCP      68     80 → 41818 [SYN, ACK] Seq=0 Ack=1 Win=65535 Len=0 MSS=1400 WS=512 SACK_PERM=1
  21093 2020-03-02 21:59:27.904154    10.9.180.89           161.117.97.14         TCP      56     41818 → 80 [ACK] Seq=1 Ack=1 Win=65536 Len=0
  21095 2020-03-02 21:59:27.904575    10.9.180.89           161.117.97.14         HTTP     463    GET /gslb/?ver=4.0&type=wap&conpt=hjgli%60%2Cir%60%2Cksii&uuid=0&list=app.chat.global.xiaomi.net%2Cresolver.msg.global.xiaomi.net&countrycode=ID&sdkver=38&osver=29&os=CPH2025%3A1582874908&mi=0&key=51b24071b1c8601c3bee862b47fe0d8f HTTP/1.1 
  21099 2020-03-02 21:59:28.046629    161.117.97.14         10.9.180.89           TCP      56     80 → 41818 [ACK] Seq=1 Ack=408 Win=1574912 Len=0
  21101 2020-03-02 21:59:28.107925    161.117.97.14         10.9.180.89           TCP      1426   80 → 41818 [ACK] Seq=1 Ack=408 Win=1574912 Len=1370 [TCP segment of a reassembled PDU]
  21102 2020-03-02 21:59:28.108332    10.9.180.89           161.117.97.14         TCP      56     41818 → 80 [ACK] Seq=408 Ack=1371 Win=68608 Len=0
  21104 2020-03-02 21:59:28.107937    161.117.97.14         10.9.180.89           HTTP     177    HTTP/1.1 200 OK  (application/json)
  21105 2020-03-02 21:59:28.108618    10.9.180.89           161.117.97.14         TCP      56     41818 → 80 [ACK] Seq=408 Ack=1492 Win=68608 Len=0
  21296 2020-03-02 21:59:43.156135    161.117.97.14         10.9.180.89           TCP      56     80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21298 2020-03-02 21:59:43.267491    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21300 2020-03-02 21:59:43.955871    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21304 2020-03-02 21:59:45.072290    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21315 2020-03-02 21:59:47.459570    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21319 2020-03-02 21:59:52.280849    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21324 2020-03-02 22:00:02.040793    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21339 2020-03-02 22:00:21.241365    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21344 2020-03-02 22:00:40.406630    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21374 2020-03-02 22:00:59.608025    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21379 2020-03-02 22:01:18.808520    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21408 2020-03-02 22:01:38.007619    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21413 2020-03-02 22:01:57.208543    161.117.97.14         10.9.180.89           TCP      56     [TCP Retransmission] 80 → 41818 [FIN, ACK] Seq=1492 Ack=408 Win=1574912 Len=0
  21418 2020-03-02 22:02:16.568119    161.117.97.14         10.9.180.89           TCP      56     80 → 41818 [RST, ACK] Seq=1493 Ack=408 Win=1574912 Len=0

The Client side did not return any messages, and the server side always re-transport fin packet(seq=1492), what caused this? App side not recv the msg?

No library found for linux to implement keyboard simulation in c++ [closed]

$
0
0

I am trying to make an application in c++ which simulates a keypress from a keyboard, meaning that if i execute the program than after that if i open any text editor it must keep on printing the character on the text editor until the c++ program is terminated. I am on Ubuntu and have not found a single way to implement it in c++

Char Driver Linux: What is the correct implementation of file_operations read and write? What are the offset checks needs to be made?

$
0
0

I am trying to read and write to a char driver. When i use a C program to open the device file and read and write it gives a SEG fault. When i use a cat to the device file it goes to infinite loop.

1) Can someone help to explain what am i missing and what is the correct implementation of read and write in file_operations?

2) I know in prototype read/write: read(struct file *fp, char *ch, size_t count, loff_t *lofft) count refers to number of bytes read/write request. But what is the last parameter offset used for and what are the checks needs to be made for offset?

3) For multiple read calls like cat /dev/chardriver will the offset be incremented for each read? Like 1st read call offset from 1 to 100 for count=100, in next read call will the offset go from 101? Or will it go from any random number?

Here is my code:

    #include <linux/module.h>
    #include <linux/kernel.h>
    #include <linux/fs.h>
    #include <linux/cdev.h>
    #include <linux/device.h>
    #include <linux/uaccess.h>

    static int device_open(struct inode *, struct file *);
    static int device_release(struct inode *, struct file *);
    static ssize_t device_read(struct file *, char *, size_t, loff_t *);
    static ssize_t device_write(struct file *, const char *, size_t, loff_t *);
    char kernelbuff[1024];

    MODULE_LICENSE("GPL");

    struct file_operations fops = {
    .read = device_read,
    .write = device_write,
    .open = device_open,
    .release = device_release
    };


    int device_open(struct inode *inode, struct file *fp)
    {
    printk("device_open called");
    return 0;
    }

    static int device_release(struct inode *inode, struct file *fp)
    {
    printk("device_release called");
    return 0;
    }

    static ssize_t device_read(struct file *fp, char *ch, size_t sz, loff_t *lofft)
    {
    printk("device_read called");      
    copy_to_user(ch, kernelbuff, 1024);
    return sz;
    }

    static ssize_t device_write(struct file *fp, const char *ch, size_t sz, loff_t *lofft)
    {
    printk("device_write called");
    copy_from_user(kernelbuff, ch, 50);
    return 1024;
    }

    static int hello_init(void)
    {
      printk("basicchardriver: module initialized");
      register_chrdev(500, "chr_device", &fops);
      return 0;
    }

    static void hello_exit(void)
    {
      printk("basicchardriver: module exited");
      unregister_chrdev(500, "chr_device");
    }

    module_init(hello_init);
    module_exit(hello_exit);
 }

To test:

sudo mknod -m 666 /dev/chardev c 500 0
echo "Hello World">> /dev/chardev    ===> Works fine
cat /dev/chardev     ===> Goes to infinite loop

If i call the driver using a C program it gives SEG fault:

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <fcntl.h>

int main()
{
  int fd;
  char buff[500];

  fd = open("/dev/chardev", O_RDWR);
  write(fd, "Hello World", 13);

  read(fd, buff, 500);
  printf("Reading data from kernel: \t");
  puts(buff);

  return 0;
}

raj@raj-VirtualBox:~/device-driver/chardriver/read-write$ ./a.out
Reading data from kernel: Hello World
*** stack smashing detected ***: <unknown> terminated
Aborted (core dumped)

High kworker CPU usage on idle embedded system

$
0
0

I am working on an embedded device where the kworker stays at high cpu usage when the device is idle.

iostat output:

bash-4.3# /intflash/iostat
Linux 4.9
         03/05/20           _ppc_   (2 CPU)

avg-cpu:  %user   %nice %system %iowait  %steal   %idle
           2.91    0.03   39.45    0.00    0.00   57.60

Device:            tps    kB_read/s    kB_wrtn/s    kB_read    kB_wrtn

bash-4.3#

CPU backtrace:

[ 5576.307579] sysrq: SysRq : Show backtrace of all active CPUs
[ 5576.312021] sysrq: CPU1:
[ 5576.312025] Call Trace:
[ 5576.312040] [e7425bc0] [c035bafc] showacpu+0x6c/0x90 (unreliable)
[ 5576.312051] [e7425be0] [c00a9f64] flush_smp_call_function_queue+0xb4/0x1a0
[ 5576.312059] [e7425c00] [c0011348] smp_ipi_demux+0xb8/0x100
[ 5576.312064] [e7425c30] [c000fa20] doorbell_exception+0x60/0x88
[ 5576.312069] [e7425c50] [c0010324] ret_from_except_full+0x0/0x4c
[ 5576.312084] --- interrupt: 2070 at udelay+0x24/0x40
                   LR = __mmc_start_request+0xac/0x120
[ 5576.312088] [e7425d10] [c049e370] __mmc_start_request+0xc0/0x120 (unreliable)
[ 5576.312094] [e7425d30] [c049e53c] mmc_start_request+0x16c/0x2f0
[ 5576.312099] [e7425d50] [c049edc0] mmc_wait_for_req+0x90/0x130
[ 5576.312104] [e7425d70] [c049eec8] mmc_wait_for_cmd+0x68/0x80
[ 5576.312110] [e7425dd0] [c04abb88] mmc_io_rw_direct_host+0x88/0x160
[ 5576.312115] [e7425e30] [c04ac05c] sdio_reset+0x2c/0xb0
[ 5576.312121] [e7425e50] [c04a2298] mmc_rescan+0x3e8/0x440
[ 5576.312129] [e7425e80] [c0043980] process_one_work+0x170/0x400
[ 5576.312133] [e7425ea0] [c0043d54] worker_thread+0x144/0x550
[ 5576.312141] [e7425ef0] [c0049974] kthread+0xd4/0xf0
[ 5576.312146] [e7425f40] [c000fdf8] ret_from_kernel_thread+0x5c/0x64

Can anyone give me some ideas on how to track the cause of this problem?

Pick up an issue in Linux kernel [closed]

$
0
0

I want to contribute to Linux kernel. I want to solve an existing issue. I have already researched on steps to submit patches and formatting style. I am clear in mind regarding the patch specifications.

I want to know how do I pick up an issue in the first place. I am interested in device driver subsystem. https://www.kernel.org/doc/html/v4.19/process/submitting-patches.html

This above URL says:

..however, that you may not want to develop against the mainline tree directly. Most subsystem maintainers run their own trees and want to see patches prepared against those trees ..

So how do I find the tree for device drivers? I then have to git clone that tree.

How does a system wide profiler (e.g. perf) correlate counters with instructions?

$
0
0

I'm trying to understand how a system wide profiler works. Let's take linux perf as example. For a certain profiling time it can provide:

  • Various aggregated hadware performance counters
  • Time spent and hardware counters (e.g. #instructions) for each user space process and kernel space function
  • Information about context switches
  • etc.

The first thing I'm almost sure about is that the report is just an estimation of what's really happening. So I think there's some kernel module that launches software interrupts at a certain sampling rate. The lower the sampling rate, the lower the profiler overhead. The interrupt can read the model specific registers that store the performance counters.

The next part is to correlate the counters with the software that's running on the machine. That's the part I don't understand.

  1. So where does the profiler gets its data from?

  2. Can you interrogate for example the task scheduler to find out what was running when you interrupted him? Won't that affect the execution of the scheduler (e.g. instead of continuing the interrupted function it will just schedule another one, making the profiler result not accurate). Is the list of task_struct objects available?

  3. How can profilers even correlate HW metrics even at instruction level?

Why ppoll() no wait my delay in Android Pie?

$
0
0

I learned that the loop that checks the GPIO interrupt, which is supposed to loop at ~100 usec, is actually looping every 3 usec. The reason is that the timespec I gave the GPIO event wait routine isn't working. The wait instantly times out.

(Note that I removed extra code, error handling, and other features that are typical in a loop... like how to exit the loop)

struct timespec timeSpec = { 0, 100000 };  // sec, nanosec

struct gpiod_line_event event;
for (;;)
{

   result = gpiod_line_event_wait(pGpioLine, &timeSpec);    // ppoll(....timeSpec) is called inside this wait() 
   if (result > 0)
   {

      // GPIO IRQ detected
       if (gpiod_line_event_read(pGpioLine, &event) >= 0)

      {
         HandleIrq();

      }
   }
   else
   {
      //  100 usec timeout

      HandleTimeout()
   }

}

I tried to work around failure to properly wait by using many approaches. Adding a usleep(1); to the for loop doesn't work. The actual sleep time is 30 to 40 msec which is too long for our driver. This wasn't a surprise as this isn't a real time OS.

I tried changing the timeSpec to have an absolute instead of a relative time. For example, I tried to create my own wait based on the REAL_TIME clock.

struct timespec timeToWait;

   clock_gettime(CLOCK_REALTIME, &timeToWait);

   timeToWait.tv_nsec += 10000000UL;

    result = gpiod_line_event_wait(pGpioLine, &timeToWait);

This didn't work and I eventually concluded that the timespec is supposed to be relative for this gpiod API. (The API is actually ppoll() )


ARM ORR register difference

$
0
0

I'm trying to understand this kernel change. It's a {get,put}_user function correction, and it includes this fix:

 #ifndef __ARMEB__
-   orr r2, r2, r3, lsl #8
+   orr r2, r2, rb, lsl #8
 #else
-   orr r2, r3, r2, lsl #8
+   orr r2, rb, r2, lsl #8
 #endif

This means OR the values in r2 and r3 and save the result to r2. For the fix, just read the value from rb instead of r3. (__ARMEB__ indicates big endian or not.)

So what does happens if this part of the fix hasn't been applied?

Reason why CFS scheduler using red black tree?

$
0
0

CFS scheduler picks next process based on minimum virtual time and to get this value efficiently its using Red-Black tree(rbtree), using rbtree we will get minimum O(h) here h is height of rbtree. But, using min-heap we can get min virtual time process in O(1) time only. I just want to know why min-heap is not consider in CFS implementation and is there any difficulties using min-heap in kernel level?

Any idea how Linux determines which string should be printed in a kernel module?

$
0
0

Given the most basic kernel module

#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/printk.h>

static int __init my_mod_init(void) {
    printk("Hello World!");
    printk("Goodbye World!");
    return 0;
}
static void __exit my_mod_exit(void) { }

module_init(my_mod_init);
module_exit(my_mod_exit);

MODULE_LICENSE("GPL");

GCC generates the following armv7 assembly (objdump)

dummy.ko:     file format elf32-littlearm

Disassembly of section .init.text:

00000000 <init_module>:
   0:   e92d4010    push    {r4, lr}
   4:   e3000000    movw    r0, #0
   8:   e3400000    movt    r0, #0
   c:   ebfffffe    bl  0 <printk>
  10:   e3000000    movw    r0, #0
  14:   e3400000    movt    r0, #0
  18:   ebfffffe    bl  0 <printk>
  1c:   e3a00000    mov r0, #0
  20:   e8bd8010    pop {r4, pc}

Disassembly of section .exit.text:

00000000 <cleanup_module>:
   0:   e12fff1e    bx  lr

The rodata section looks like this:

Contents of section .rodata.str1.4:
 0000 48656c6c 6f20576f 726c6421 00000000  Hello World!....
 0010 476f6f64 62796520 576f726c 642100    Goodbye World!. 

I at least expected r0 at lines 0x10 and 0x14 to be something like mov r0, #16 or ldr r0, [pc, #12]. How is the second printk function informed to print "Goodbye World!"?

Vulnerabilities of Linux Kernel While Scanning Docker Images in AWS ECR

$
0
0

We are using AWS ECR for managing docker images. I enabled "Scan on push" while creating repository. We are building the docker images on Linux Kernel which has version of "5.3.0-40-generic".

After Pushing those images to repository, I see a few Critical Vulnerabilities. I am getting the Link for every issue. I tried understanding each issue.

If the issue is fixed, they are saying to use the package with different version which is fixed.

How can i install the fixed version while building the docker image?

Halt instruction from Linux kernel module is not working

$
0
0

I wrote a simple Linux kernel module to issue hlt instruction

#include <linux/kernel.h>
#include <linux/module.h>

MODULE_LICENSE("GPL");
static int __init test_hello_init(void)
{
    asm("hlt");
    return 0;
}

static void __exit test_hello_exit(void)
{
}

module_init(test_hello_init);
module_exit(test_hello_exit);

Loading this module on my Virtual Machine, I don't see my VM is halted.

Am I missing something?

How to write to protected pages in the Linux kernel?

$
0
0

I am trying to add a syscall in a module. My rationale is:

  1. This is for a research project, so the exact implementation does not matter.
  2. Adding syscalls in the kernel-core takes a prohibitively long time to re-compile. I can suck up compiling once with an expanded syscall table, but not every time. Even with incremental compiling, linking and archiving the final binary takes a long time.
  3. Since the project is timing sensitive, using kprobes to intercept the syscall handler would slow down the syscall handler.

I am still open to other means of adding a syscall, but for the above reasons, I think that writing to the sys_call_table in a module is the cleanest way to do what I am trying to do.

I've gotten the address of the syscall table from the System.map, disabled kaslr, and I am trying to clear the page protections, but some write-protection is still holding me back.

// following https://web.iiit.ac.in/~arjun.nath/random_notes/modifying_sys_call.html

// clear cr0 write protection
write_cr0 (read_cr0 () & (~ 0x10000));

// clear page write protection
sys_call_table_page = virt_to_page(&sys_call_table[__NR_execves]);
set_pages_rw(sys_call_table_page, 1);

// do write
sys_call_table[__NR_execves] = sys_execves;

However, I'm still getting a permission error, but I don't know the mechanism by which it is enforced:

[   11.145647] ------------[ cut here ]------------
[   11.148893] CR0 WP bit went missing!?
[   11.151539] WARNING: CPU: 0 PID: 749 at arch/x86/kernel/cpu/common.c:386 native_write_cr0+0x3e/0x70
...
Here was a call trace pointing to the write of sys_call_table
...
[   11.332825] ---[ end trace c20c95651874c08b ]---
[   11.336056] CPA  protect  Rodata RO: 0xffff888002804000 - 0xffff888002804fff PFN 2804 req 8000000000000063 prevent 0000000000000002
[   11.343934] CPA  protect  Rodata RO: 0xffffffff82804000 - 0xffffffff82804fff PFN 2804 req 8000000000000163 prevent 0000000000000002
[   11.351720] BUG: unable to handle page fault for address: ffffffff828040e0
[   11.356418] #PF: supervisor write access in kernel mode
[   11.359908] #PF: error_code(0x0003) - permissions violation
[   11.363665] PGD 3010067 P4D 3010067 PUD 3011063 PMD 31e29063 PTE 8000000002804161
[   11.368701] Oops: 0003 [#1] SMP KASAN PTI

full dmesg

Any guesses on how to disable it?

Different ways of suppressing 'uninitialized variable warnings' in C

$
0
0

I have encountered multiple uses of the uninitialized_var() macro designed to get rid of warnings like:

warning: ‘ptr’ is used uninitialized in this function [-Wuninitialized]

For GCC (<linux/compiler-gcc.h>) it is defined such a way:

/*
 * A trick to suppress uninitialized variable warning without generating any
 * code
 */
#define uninitialized_var(x) x = x

But also I discovered that <linux/compiler-clang.h> has the same macro defined in a different way:

#define uninitialized_var(x) x = *(&(x))

Why we have two different definitions? For what reason the first way may be insufficient? Is the first way insufficient just for Clang or in some other cases too?


example:

#define uninitialized_var(x) x = x

struct some {
     int a;
     char b;
};

int main(void) {
     struct some *ptr;
     struct some *uninitialized_var(ptr2);

     if (1)
         printf("%d %d\n", ptr->a, ptr2->a); // warning about ptr, not ptr2
}

Linux - list of registered devices

$
0
0

I have a linux driver that registers a char device for every compatible device-node in the Flattened-Device-Tree(FDT).

On initialization, the driver allocates a major device number and a range of minor device numbers. when i look at /proc/devices, this major device number is listed.

Now, when I define 2 device-nodes, compatible with that driver, in the FDT, the driver's platform-probe-function get's called twice, and 2 char devices are registered under the same major device number, but with ascending minor device numbers.

Since I can lookup the major number, and I do know how many devices I have and that the minor numbers start at 0, I can just type mknod -m 666 /dev/mydevice1 c 246 0 and mknod -m 666 /dev/mydevice2 c 246 1 to create device nodes for the two char devices.

But I am wondering if there is a way I can lookup all the devices known to the system with their major and minor device numbers, so I do not have to know the minor number beforehand, in order to be able to create device nodes for those devices?

Building an out-of-tree linux kernel module with separate output directory

$
0
0

I want to build an out of tree kernel module with the output directory being separate from my source directory? How would I do this? I'm willing to go any route. I'm okay with minimal changes to the kernel build system, I'm okay with copying source files (however I do not want to rebuild if I haven't made any changes to the source files and this doesn't work if I copy source files normally), and I'm okay with setting a parameter or something.

seq_file not working properly after next returns NULL

$
0
0

What is wrong with this code (I guess with regard to compatibility with different kernel versions)?

#define BUFFER_SIZE 2048
#define BUFFER_STEP 128

static char buffer[BUFFER_SIZE] = { 0 }; // this is filled with repeating letters a-z in module init

static void* seqf_ex_start (struct seq_file* m, loff_t* pos)
{
    if (*pos >= BUFFER_SIZE) {
        return NULL;
    }

    return buffer + *pos;
}

static void* seqf_ex_next (struct seq_file* m, void* v, loff_t* pos)
{
    *pos += BUFFER_STEP;

    if (*pos >= BUFFER_SIZE) {
        return NULL;
    }

    return buffer + *pos;
}

static int seqf_ex_show (struct seq_file* m, void* v)
{
    seq_printf(m, "%.*s\n", BUFFER_STEP, (char*)v);

    return 0;
}

When running the kernel module in qemuarm (kernel v5.0.19), I get the correct output:

$ cat /proc/seqf-ex | awk '{ print "line" OFS NR ":" OFS length($0) }'
line 1: 128
line 2: 128
line 3: 128
line 4: 128
line 5: 128
line 6: 128
line 7: 128
line 8: 128
line 9: 128
line 10: 128
line 11: 128
line 12: 128
line 13: 128
line 14: 128
line 15: 128
line 16: 128

But when running on kernel v4.15.0, I get this:

$ cat /proc/seqf-ex | awk '{ print "line" OFS NR ":" OFS length($0) }'
line 1: 128
line 2: 128
line 3: 128
line 4: 128
line 5: 128
line 6: 128
line 7: 128
line 8: 128
line 9: 128
line 10: 128
line 11: 128
line 12: 128
line 13: 128
line 14: 128
line 15: 128
line 16: 128
line 17: 127
line 18: 126
line 19: 125
line 20: 124
line 21: 123
line 22: 122
line 23: 121
line 24: 120
line 25: 119
line 26: 118
line 27: 117
line 28: 116
line 29: 115
line 30: 114
line 31: 113
line 32: 112
line 33: 111
line 34: 110
line 35: 109
line 36: 108
line 37: 107
line 38: 106
line 39: 105
line 40: 104
line 41: 103
line 42: 102
line 43: 101
line 44: 100
line 45: 99
line 46: 98
line 47: 97
line 48: 96
line 49: 95
line 50: 94
line 51: 93
line 52: 92
line 53: 91
line 54: 90
line 55: 89
line 56: 88
line 57: 87
line 58: 86
line 59: 85
line 60: 84
line 61: 83
line 62: 82
line 63: 81
line 64: 80
line 65: 79
line 66: 78
line 67: 77
line 68: 76
line 69: 75
line 70: 74
line 71: 73
line 72: 72
line 73: 71
line 74: 70
line 75: 69
line 76: 68
line 77: 67
line 78: 66
line 79: 65
line 80: 64
line 81: 63
line 82: 62
line 83: 61
line 84: 60
line 85: 59
line 86: 58
line 87: 57
line 88: 56
line 89: 55
line 90: 54
line 91: 53
line 92: 52
line 93: 51
line 94: 50
line 95: 49
line 96: 48
line 97: 47
line 98: 46
line 99: 45
line 100: 44
line 101: 43
line 102: 42
line 103: 41
line 104: 40
line 105: 39
line 106: 38
line 107: 37
line 108: 36
line 109: 35
line 110: 34
line 111: 33
line 112: 32
line 113: 31
line 114: 30
line 115: 29
line 116: 28
line 117: 27
line 118: 26
line 119: 25
line 120: 24
line 121: 23
line 122: 22
line 123: 21
line 124: 20
line 125: 19
line 126: 18
line 127: 17
line 128: 16
line 129: 15
line 130: 14
line 131: 13
line 132: 12
line 133: 11
line 134: 10
line 135: 9
line 136: 8
line 137: 7
line 138: 6
line 139: 5
line 140: 4
line 141: 3
line 142: 2
line 143: 1

It seems that seqf_start function is called repeatedly after the seqf_next returns NULL. Why is this happening?

Memory map AXI DMA scatter/gather mode registers to userspace

$
0
0

I am new to the area of DMA and Kernel Programming, so please pardon me if it is a naive question.

I am writing a kernel driver which can expose kernel memory to user space for dma related operations (in context of a nic).

I came across uio. And I am trying to implement something similar to it.

How do I map DMA's scatter gather mode registers to user space?

Here is my current approach:

First I get the bus address for the base:

addr = pci_resource_start(pci_dev, DMA_AXI_BAR) + DMA_HARDWARE_OFFSET

I tried to map this address directly using remap_pfn_range by giving addr obtained in above step to this method.

But I am getting a 'corrupted page table exception'.

Any help would be highly appreciated.

I am using Linux Kernel 4.15.

Why do we need DMA pool?

$
0
0

I'm reading https://www.kernel.org/doc/Documentation/DMA-API.txt and I don't understand why DMA pool is needed.

Why not having PAGE_SIZE DMA allocated memory dma_alloc_coherent and use offsets?

Also, why is dynamic DMA useful for networking device driver instead of reusing the same DMA memory?

What is the most performant for <1KB data transfers?

Viewing all 12198 articles
Browse latest View live


<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>