mirror of
https://github.com/outbackdingo/UltraGrid.git
synced 2026-03-21 10:40:21 +00:00
* format is now entered as a parameter string (-g <mode>) * expect currently buffers as big as needed (exactly one frame) TODO: revide if isn't possible to read whole buffer at once (ideally the memmapped one, and extract frames by hand) * now it is needed to set /sys/class/sdivideo/sdivideorxX/bufsize * bump to new driver (2.7.2)
83 lines
2.9 KiB
Plaintext
83 lines
2.9 KiB
Plaintext
This file describes how memory for DMA buffers is allocated
|
|
by the Master Linux driver. It is primarily of interest
|
|
to programmers who wish to modify the driver.
|
|
|
|
The Master Linux driver provides several DMA buffers
|
|
for each interface. These buffers can range in size from
|
|
a few bytes to several thousand bytes, may be different
|
|
for each interface, and may number in the thousands.
|
|
Allocating this memory becomes complex because of
|
|
the limitations of the methods available to request
|
|
DMA-capable memory in the Linux kernel.
|
|
|
|
There are two basic methods of allocating DMA-capable memory
|
|
in the Linux kernel:
|
|
|
|
kmalloc() can allocate
|
|
32 bytes, 64 bytes, 128 bytes,..., 131072 bytes
|
|
in contiguous blocks.
|
|
|
|
get_free_page() allocates one page.
|
|
On the x86, one page is 4096 bytes.
|
|
|
|
Allocating contiguous blocks becomes difficult as larger blocks
|
|
are requested and memory becomes scarce.
|
|
|
|
Allocating each buffer with a single kmalloc() is not acceptable
|
|
because it is difficult or impossible to get larger blocks.
|
|
|
|
Allocating each buffer with multiple get_free_page() calls
|
|
is not acceptable because the memory wasted by smaller buffers
|
|
is excessive.
|
|
|
|
There are also issues in allocating memory for
|
|
pointers to buffers and DMA descriptors.
|
|
|
|
At present, memory allocation works like this:
|
|
|
|
Memory for all of the buffers is allocated with get_free_page().
|
|
For DVB ASI, the "tails" of buffers which are not integer multiples
|
|
of the page size are "packed" into pages at the end of this memory;
|
|
ie. several buffers may share a single page.
|
|
For raw SDI and SDI audio/video, each tail has its own page.
|
|
The pointers to these pages are stored in a kmalloc'd array.
|
|
Another kmalloc'd array is used to store pointers to each page
|
|
and tail in the order they will be accessed.
|
|
|
|
Memory for the DMA descriptors is allocated with multiple
|
|
pci_pool_alloc() calls. Pointers to these descriptors are stored
|
|
in a kmalloc'd array.
|
|
|
|
Example:
|
|
|
|
Suppose we want one thousand 9588-byte buffers for
|
|
one DVB ASI interface. Each buffer is made up of two 4096-byte pages
|
|
plus one 1396-byte tail. Since up to two tails can fit
|
|
in one page, the buffers will fit in 2500 pages.
|
|
Tails are never split between multiple pages.
|
|
Assuming 32-bit pointers, the 2500 pointers to these pages
|
|
will fit in a 16384-byte array. Another 16384-byte array
|
|
will hold the 3000 pointers to the pages and tails in
|
|
the order they will be accessed.
|
|
|
|
The total memory required for this example is
|
|
1000 * 9588 + 2500 * 4 + 3000 * 4 = 9610000 bytes.
|
|
The memory actually allocated is
|
|
2500 * 4096 + 16384 + 16384 = 10272768 bytes.
|
|
|
|
|
|
Example:
|
|
|
|
Suppose we want ten thousand 1316-byte buffers
|
|
for one DVB ASI interface. Since three buffers will fit in one page,
|
|
all of the buffers will fit in 3334 pages. The 3334 pointers
|
|
to these pages will fit in a 16384-byte array,
|
|
and the 10000 pointers to the buffers will fit
|
|
in a 65536-byte array.
|
|
|
|
This example requires
|
|
10000 * 1316 + 3334 * 4 + 10000 * 4 = 13213336 bytes
|
|
and allocates
|
|
3334 * 4096 + 16384 + 65536 = 13737984 bytes.
|
|
|