ALSA unable to use dmix with route [closed] - alsa

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.
Closed 2 years ago.
Improve this question
I have an alsa config file which I use to map stereo speakers on to my 5.0 speaker setup.
The file looks like this:
pcm.all8 {
type plug
slave {
pcm "hw:0,0"
channels 8
}
hint.description "8 channel analog"
}
pcm.music4 {
type route
slave {
pcm all8
channels 8
}
ttable {
0.0 1
1.1 1
0.2 1 # Copy Front Left to Rear Left
1.3 1 # Copy Front Right to Rear Right
0.4 0.8 # Copy Front Left to Front Centre
1.4 0.8 # Copy Front Right to Front Centre
}
hint.description "2 channels duplicated on front and rear"
}
I currently use the "music4" device to play music from one program but I now need a second program to have access to the device too. I need to use dmix as, currently, the device is locked.
I tried adding this to the config (which I shamelessly copied from https://www.alsa-project.org/main/index.php/Asoundrc#dmix):
pcm.dmixer {
type dmix
ipc_key 1024
slave {
pcm music4
period_time 0
period_size 1024
buffer_size 4096
rate 44100
}
bindings {
0 0
1 1
}
hint.description "Dmixed - 4 speakers"
}
When I try to use this device I get an error message saying "dmix plugin can be only connected to hw plugin" but how can I do that while preserving my mappings?

Managed to work this one out. Solution looks like this:
pcm.dmixer {
type dmix
ipc_key 1024
ipc_key_add_uid true
slave {
pcm "hw:0,0"
period_time 0
period_size 1024
buffer_size 4096
rate 44100
channels 8
}
bindings {
0 0
1 1
2 2
3 3
4 4
5 5
6 6
7 7
}
hint.description "Raw dmixer - 8 channels"
}
pcm.dmix4 {
type plug
slave.pcm dmixer
slave.channels 8
ttable {
0.0 1
1.1 1
0.2 1 # Copy Front Left to Rear Left
1.3 1 # Copy Front Right to Rear Right
0.4 0.8 # Copy Front Left to Front Centre
1.4 0.8 # Copy Front Right to Front Centre
}
hint.description "Dmixed - 2 channels to 5.0"
}

Related

FreeRTOS priority 1 is special?

FreeRTOS priority 1 is special?
In my system,i have 6 priority 0-5. I know the idle pro at 0.
i assign a task at 1,others at 2-5.from the cpu time and IDEL pro info ,i could know the cpu have enough time to do all tasks.
I found a problem that the task at 1 could not work at the right time,the frequence is 10Hz,but i found sometimes it not work. maybe 8 or lower than 10,even lower than 1Hz.
when i set the task at 2,it's ok,work at 10Hz.
The code struct like this:
void SYS_MONITOR::run(){
int ret = 0;
while(1){
vTaskDelayUntil(&last_wake_time, SYS_MONITOR_RUN_INTERVAL_MS/portTICK_RATE_MS);
dosomething....
}
ID State Prio Mark CPU(%) Name
1 S 1 261 0.0000000 God
2 R 0 109 69.6136779 IDLE
3 S 5 470 3.9053585 Tmr Svc
...
...
44 B 2 179 0.0242588 SYS_MONITOR_run
Heap : Total 491520 , Used 193696 , Remain 297824
DmaHeap: Total 16384 , Used 2048 , Remain 14336
There is no enough information to answer this.
You have quite large setup , by looking at the number of tasks you have.
One thing :
1 S 1 261 0.0000000 God
.....
4 B 2 179 0.0242588 SYS_MONITOR_run
5 R 1 303 0.0142761 SYS_CLI_SERV_run
You have at least 2 Tasks with priority 1 there. If your SYS_MONITOR_run was 1 also and started working "better" after you bumped it's priority to 2 (higher) that is not surprising.
It depends on your scheduler configuration how the equal priority tasks get chance to run, e.g.: do you have time slicing round-robin or FIFO on equal priority tasks? That's one. ...
Two, you have complex setup (44 Tasks!) and too little info to really answer your question.

Add elements to head of array while removing from tail [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 7 years ago.
Improve this question
I have an array x of constant size (usually around 100-200 entries) and would like to add an array y of constant smaller size (usually between 2-10 entries) to the head, while removing the same size at the end. For example:
Buffer:
x = [6 5 4 3 2 1]
New array to add in front:
y = [8 7]
Resulting buffer:
x = [8 7 6 5 4 3]
And so on...
Note: I need to use a regular C array and need to be able to access the whole array, not only the head or tail. The array is rather small, but the function is called very often, so I am looking for a solution that does not require any excessive memory tasks. Arrays x and y are always of the same size in each step.
Is this a buffer, circular / ring buffer, queue or FIFO? I don't really know what the right search term is for this application.
Language is C.
If you require linear access to the array contents, and you want to not perform frequent memcpy operations, a possible solution for this is a flip buffer or sliding buffer.
The flip buffer is twice as large as the array needs to be (or even more, if you like), so that you can can just move a tail pointer when adding to the end without any wraparound, keeping the data linear.
When you hit the hard limit of the underlying buffer, then you do a slide operation: you move the upper half of the array to the lower half, and subtract the same delta from all the indices.
When this slide operation happens, you know that all data and indices are in the upper partition now, because the buffer, which is 2 * N, wide never contains more than N entries: it is simulating an N sized ring buffer. That is to say, a situation never arises that the tail has hit the end of the buffer, but the head is still in the lower partition (there are more than N items).
Since you'd like to add to the front, we start by filling the upper partition, and we flip in the upward direction:
[x x x x x x | 6 5 4 3 2 1 ] -- six-element queue, twelve el. buffer
H T
Add 8 7, remove 2 1:
[x x x x 8 7 | 6 5 4 3 x x ]
H T
Add 2 1 0 9, remove 6 5 4 3:
[2 1 0 9 8 7 | x x x x x x ]
H T
Head has hit -1! Flip to upper partition with memcpy, add 6 to head and tail:
[x x x x x x | 2 1 0 9 8 7 ]
H T
Note that since the two partitions don't overlap, we don't have to use memmove: we can use memcpy.
What about using memmove() from <string.h> to move slices of the array around? That's not something to exclude without having actually measured the performance. Any solution using linked lists or so might involve operations that take longer than a highly optimized memmove() (that the compiler might even inline).
It really depends on
the number of elements in the array
the size of the element type
the frequency of the operations
the time spent modifying the array with respect to everything else
What you need is index offset. So, every time you "insert" values, you simply write them where you virtual tail is and update index offset. That is how circular buffers work.
This is a duplicate. Here's a Java implementation in full on code review https://codereview.stackexchange.com/questions/64258/array-implementation-of-queue and one of the questions in C here Queue using Arrays.

Read and display gray scale images in C language.

I want to load gray scale images in C, pre process it and then display the modified image. My question is:
What is the right way to import gray scale images(jpeg,png formats)in C language ?
My own search before asking this question.
1- fread or with file management, we can read image but data will be encrypted(compressed), I want gray scale values(0-255) of each pixel.
2- There is one API ImageMagick which can be helpful but it is having installation problem with Mac OS X.
I have done image processing in python and matlab but have no idea about C language.
Thanks
You have a number of options, but I will go through them starting with the easiest and least integrated with OSX, and getting progressively more integrated with OSX.
Easiest Option
Personally, if I was intent on processing greyscale images, I would write my software to use NetPBM's Portable Greymap (PGM) format as that is the very simplest to read and write and readily interchangeable with other formats. There is no compression, DCT, quantisation, colorspaces, EXIF data - just your data with a simple header. The documentation is here.
Basically a PGM file looks like this:
P2
# Shows the word "FEEP" (example from Netpbm man page on PGM)
24 7
15
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 3 3 3 3 0 0 7 7 7 7 0 0 11 11 11 11 0 0 15 15 15 15 0
0 3 0 0 0 0 0 7 0 0 0 0 0 11 0 0 0 0 0 15 0 0 15 0
0 3 3 3 0 0 0 7 7 7 0 0 0 11 11 11 0 0 0 15 15 15 15 0
0 3 0 0 0 0 0 7 0 0 0 0 0 11 0 0 0 0 0 15 0 0 0 0
0 3 0 0 0 0 0 7 7 7 7 0 0 11 11 11 11 0 0 15 0 0 0 0
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
You can see the P2 says it is in ASCII (easy to read) and a greymap. Then the next line says it is 24 pixels wide by 7 tall and that the brightest pixel is 15. Very simple to read and write. You can change the P2 to P5 and write everything after the MAXVAL in binary to save space.
Now you can just use ImageMagick outside your program to convert JPEG, PNG, GIF, TIFF files to PGM like this - without needing any linking or libraries or compiler switches:
convert input.png output.pgm
convert input.jpg output.pgm
Likewise, when you have finished processing and created your resulting output file in PGM format you can convert it to JPEG or TIFF by simply reversing the parameters:
convert result.pgm result.jpg
Personally, I would install ImageMagick using homebrew. You go to the homebrew website and copy the one-liner and paste it into a terminal to install homebrew. Then you can install ImageMagick with:
brew install imagemagick
and, by the way, if you want to try out the other suggestion here, using OpenCV, then that is as easy as
brew search opencv
brew install homebrew/science/opencv
If you want a small, self-contained example of a little OpenCV project, have a look at my answer to another question here - you can also see how a project like that is possible from the command line with ImageMagick in my other answer to the same question.
Magick++
If you choose to install ImageMagick using homebrew you will get Magick++ which will allow you to write your algorithms in C and C++. It is pretty easy to use and can run on any platforms, including OSX and Windows and Linux so it is attractive from that point of view. It also has many, many image-processing functions built right in. There is a good tutorial here, and documentation here.
Your code will look something like this:
// Read an image from URL
Image url_image("http://www.serverName.com/image.gif");
// Read image from local filesystem
Image local_file_image("my_image.gif");
// Modify image
Pixels my_pixel_cache(my_image);
PixelPacket* pixels;
// define the view area that will be accessed via the image pixel cache
int start_x = 10, start_y = 20, size_x = 200, size_y = 100;
// return a pointer to the pixels of the defined pixel cache
pixels = my_pixel_cache.get(start_x, start_y, size_x, size_y);
// set the color of the first pixel from the pixel cache to black (x=10, y=20 on my_image)
*pixels = Color("black");
// set to green the pixel 200 from the pixel cache:
// this pixel is located at x=0, y=1 in the pixel cache (x=10, y=21 on my_image)
*(pixels+200) = Color("green");
// now that the operations on my_pixel_cache have been finalized
// ensure that the pixel cache is transferred back to my_image
my_pixel_cache.sync();
// Save results as BMP file
image.write(“result.bmp”);
Apple OSX Option
The other ENTIRELY SEPARATE option would be to use the tools that Apple provides for manipulating images - they are fast and easy to use, but are not going to work on Linux or Windows. So, for example, if you want to
a) load a PNG file (or a TIFF or JPEG, just change the extension)
b) save it as a JPEG file
c) process the individual pixels
// Load a PNG file
NSImage * strImage = [[NSImage alloc]initWithContentsOfFile:#"/Users/mark/Desktop/input.png"];
// Save NSImage as JPG
NSData *imageData = [strImage TIFFRepresentation];
NSBitmapImageRep *imageRep = [NSBitmapImageRep imageRepWithData:imageData];
NSDictionary *imageProps = [NSDictionary dictionaryWithObject:[NSNumber numberWithFloat:1.0] forKey:NSImageCompressionFactor];
imageData = [imageRep representationUsingType:NSJPEGFileType properties:imageProps];
[imageData writeToFile:#"/Users/Mark/Desktop/result.jpg" atomically:YES];
// Access individual pixels
int w=imageRep.pixelsWide;
int h=imageRep.pixelsHigh;
int bps=imageRep.bitsPerSample;
printf("Dimensions: %dx%d\n",w,h);
printf("bps: %d\n",bps);
// Get a pointer to the uncompressed, unencoded pixel data
unsigned char *pixelData = [imageRep bitmapData];
for(int j=0;j<10;j++){
printf("Pixel %d: %d\n",j,pixelData[j]);
}
Of course, you could take the code above and easily make a little utility that converts any file format to PGM and then you could go with my first suggestion of using PGM format and wouldn't need to install ImageMagick - although it is actually dead simple with homebrew.
Bear in mind that you can mix Objective-C (as in the last example) with C++ and C in a single project using clang (Apple's compiler), so you can go ahead in C as you indicate in your question with any of the examples I have given above.
If you are new to developing on OSX, you need to go to the AppStore and download, for free, Apple's Xcode to get the compiler and libraries. Then you must do
xcode-select --install
to install the command-line tools if you wish to do traditional development using Makefiles and command-line compilation/linking.
This answer is an attempt to demonstrate how to develop with ImageMagick's MagickWand API with Xcode, and is based on the comments from the OP.
After installing ImageMagick, start a new Xcode command-line C project. Before writing any code, you need to tell llvm about the ImageMagick resources/libraries/etc.
There are many, many, ways to achieve this, but here's the quickest I can think of.
Navigate to top-level project's "Build Settings"
Under "All" (not "Basic") search for "Other Linker Flags"
Outside of Xcode, open up Terminal.app and enter the following
MagickWand-config --ldflags
Enter the output from Terminal.app as the value for "Other Linker Flags"
Back in the settings search; enter "Other C Flags"
Back in Terminal.app run the following
MagickWand-config --cflags
Enter the resulting output as the value for "Other C Flags"
Over in file main.c, you should notice Xcode picking-up MagickWand commands right away.
Try the following (needs X11 installed) ...
#include <stdio.h>
#include <wand/MagickWand.h>
int main(int argc, const char * argv[]) {
MagickWandGenesis();
MagickWand * wand;
wand = NewMagickWand();
MagickReadImage(wand, "wizard:");
MagickQuantizeImage(wand, 255, GRAYColorspace, 0, MagickFalse, MagickTrue);
MagickDisplayImage(wand, ":0");
wand = DestroyMagickWand(wand);
MagickWandTerminus();
return 0;
}
... and build + run to verify.
edit
To get the gray scale (0-255) value for each pixel, you can invoke a pixel iterator (see second example here), or export the values. Here is an example of dynamically populating a list of gray values by exporting...
// Get image size from wand instance
size_t width = MagickGetImageWidth(wand);
size_t height = MagickGetImageHeight(wand);
size_t total_gray_pixels = width * height;
// Allocate memory to hold values (total pixels * size of data type)
unsigned char * blob = malloc(total_gray_pixels);
MagickExportImagePixels(wand, // Image instance
0, // Start X
0, // Start Y
width, // End X
height, // End Y
"I", // Value where "I" = intensity = gray value
CharPixel, // Storage type where "unsigned char == (0 ~ 255)
blob); // Destination pointer
// Dump to stdout
for (int i = 0; i < total_gray_pixels; i++ ) {
printf("Gray value # %lux%lu = %d\n", i % width, i / height, (int)blob[i]);
}
/** Example output...
* Gray value # 0x0 = 226
* Gray value # 1x0 = 189
* Gray value # 2x0 = 153
* Gray value # 3x0 = 116
* Gray value # 4x0 = 80
* ... etc
*/
You can install ImageMagick on OS/X with this command:
sudo port install ImageMagick
You can get the macports package from https://www.macports.org
Don't have much experience with Mac's but I have quite a lot with OpenCV. Now granted a lot of OpenCV is in C++ (which may or may not be a problem) however it definitely supports everything you want to do and more. It's very easy to work with has lot's of helpful wiki's and a very good community.
Link to installing on Mac: http://blogs.wcode.org/2014/10/howto-install-build-and-use-opencv-macosx-10-10/
Link to some OpenCV wikis: http://opencv.org/documentation.html
EDIT:
I should also mention that older versions of OpenCV are in C and a lot of the functions are still supported if you chose to go the C route.

Plotting data included in script fails in loop

I would like to plot data points included inside a script file.
This should be done multiple times (plotting to different files).
Therefore, I am using a do-for-loop.
This loop let's Gnuplot freeze on excution.
Could you please hint me to the cause?
This is my MWE:
reset
set autoscale
do for [index=1:1] {
plot "-" with lines ls 2 notitle
0.500 5
1.000 6
1.500 7
e
}
Yes, seems like the combination of do for with inline data isn't supported. It also wouldn't be very convenient, since this would require a separate data block for every iteration like in
set style data linespoints
plot '-' using 1:2, '-' using 1:3
1 2 3
4 5 6
e
1 2 3
4 5 6
e
With version 5.0 inline data blocks were introduced which allow reusing inline data:
$data <<EOD
1 2 3
4 5 6
EOD
do for [i=2:3] {
plot $data using 1:i w l
pause -1
}

inet_pton() counterpart for link layer address

I have two problems related to my implementation -
I need a function which can convert a given link-layer address from text to standard format like we have a similar function at n/w layer for IP addresses inet_pton() which converts a given IP address from text to standard IPv4/IPv6 format.
Is there any difference b/w Link-layer address and 48-bit mac address
(in case of IPv6 specifically)?
If no, then link layer address should always also be of 48 bit in length, if I am not wrong.
Thanks in advance. Please excuse if I am missing something trivial.
EDIT :
Ok.. I am clear on the difference b/w link layer address and ethernet mac address. There are several types of data link layer addresses, ethernet mac address is just one.
Now, this arises one more problem ... As i said in my first question I need to convert a link layer address given from command line to its standard form. The solution provided here will just work for ethernet mac address only.
Isn't there any standard function for the purpose ? What I would like to do is to create an application where user will enter values for different options present in ICMP router advertisement message as stated in RFC 4861.
Option Formats
Neighbor Discovery messages include zero or more options, some of
which may appear multiple times in the same message. Options should
be padded when necessary to ensure that they end on their natural
64-bit boundaries. All options are of the form:
0 1 2 3
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Type | Length | ... |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
~ ... ~
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
Fields:
Type 8-bit identifier of the type of option. The
options defined in this document are:
Option Name Type
Source Link-Layer Address 1
Target Link-Layer Address 2
Prefix Information 3
Redirected Header 4
MTU 5
Length 8-bit unsigned integer. The length of the option
(including the type and length fields) in units of
8 octets. The value 0 is invalid. Nodes MUST
silently discard an ND packet that contains an
option with length zero.
4.6.1. Source/Target Link-layer Address
0 1 2 3
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Type | Length | Link-Layer Address ...
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
Fields:
Type
1 for Source Link-layer Address
2 for Target Link-layer Address
Length The length of the option (including the type and
length fields) in units of 8 octets. For example,
the length for IEEE 802 addresses is 1
[IPv6-ETHER].
Link-Layer Address
The variable length link-layer address.
The content and format of this field (including
byte and bit ordering) is expected to be specified
in specific documents that describe how IPv6
operates over different link layers. For instance,
[IPv6-ETHER].
One more thing I am not quite handy with C++, can you please provide a C alternative ?
Thanks.
Your first question, it's not that hard to write, and since MAC addresses are represented by a 6 byte array you don't need to take machine-dependency into account ( like endian-ness and stuff )
void str2MAC(string str,char* mac) {
for(int i=0;i<5;i++) {
string b = str.substr(0,str.find(':'));
str = str.substr(str.find(':')+1);
mac[i] = 0;
for(int j=0;j<b.size();b++) {
mac[i] *= 0x10;
mac[i] += (b[j]>'9'?b[j]-'a'+10:b[j]-'0');
}
}
mac[5] = 0;
for(int i=0;i<str.size();i++) {
mac[5] *= 0x10;
mac[5] += (str[i]>'9'?str[i]-'a'+10:str[i]-'0');
}
}
About your second question, IP ( and IPv6 specifically) is a Network Layer protocol and is above the Link Layer, thus doesn't have to do anything with the Link Layer.
If by Link Layer you mean Ethernet, yes Ethernet Address is always 48bits, but there are other Link Layer protocols presents which may use other formats.

Resources