I'm having some issues getting one (or two) of my XS-wrapped C functions to work correctly, and I've been at this for a couple of days now. Essentially, the code generates and registers a custom character for an LCD display, and then displays it. I have added the XS code for the two functions, the function declarations, a C example that works (prints the defined char), and a Perl example that doesn't (print the char). I do not know whether it's the lcdPutchar() or lcdCharDef() that's the issue, as there's no way to read the register in the LCD for the registered char.

I apologize for the length. I'm hoping by posting this (per usual), that it'll just click. Otherwise, I'm hoping someone more familiar with C/XS can perhaps spot something.

In the lcd_char_def() Perl module function, I *think* I'm generating the proper data with pack() to send to the C function (as when I printf() out the values of the array, each elem matches what I send in with a C program directly.

Here is the XS code that covers the two external C functions:

void lcdCharDef(fd, index, data) int fd int index unsigned char * data void lcdPutchar(fd, data) int fd unsigned char data

Here is the C declarations:

extern void lcdCharDef(const int fd, int index, unsigned char data [8] +); extern void lcdPutchar(const int fd, unsigned char data);

Here is the Perl module code that calls the XS:

sub lcd_char_def { shift if @_ == 4; my ($fd, $index, $data) = @_; my $unsigned_char = pack "V0C*", @$data; lcdCharDef($fd, $index, $unsigned_char); } sub lcd_put_char { shift if @_ == 3; my ($fd, $data) = @_; lcdPutchar($fd, $data); }

A short C program which prints out the proper custom character to my LCD:

#include <stdio.h> #include <wiringPi.h> #include <lcd.h> int main (int argc, char *argv[]){ unsigned char newChar [8] = { 0b11111, 0b10001, 0b10001, 0b10101, 0b11111, 0b10001, 0b10001, 0b11111, }; wiringPiSetupGpio(); static int fd; fd = lcdInit(2, 16, 4, 23, 16, 5, 6, 13, 19, 0, 0, 0, 0); lcdClear(fd); lcdPosition(fd, 0, 0); lcdCharDef(fd, 2, newChar); lcdPutchar(fd, 2); sleep(1); return 0; }

...and the Perl code that *should* do the same thing (print the custom char):

use warnings; use strict; use WiringPi::API qw(:all); setup_gpio(); my %args = ( cols => 16, rows => 2, bits => 4, rs => 23, strb => 16, d0 => 5, d1 => 6, d2 => 13, d3 => 19, d4 => 0, d5 => 0, d6 => 0, d7 => 0, ); my $fd = lcd_init(%args); my $def = [ 0b11111, 0b10001, 0b10001, 0b10101, 0b11111, 0b10001, 0b10001, 0b11111, ]; lcd_clear($fd); lcd_position($fd, 0, 0); lcd_char_def($fd, 2, $def); lcd_put_char($fd, 2); sleep 1;

Is there anything glaring that I'm missing? All of my other Perl code works fine (ie. all wrapped C functions work properly in all other cases. It's just one or both of these two that don't).


In reply to [SOLVED (workaround)]: External C function called through XS not Doing The Right Thing by stevieb

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.