Recent

Author Topic: Zbarcam SIGSEGV Error  (Read 7250 times)

Stygian

  • Jr. Member
  • **
  • Posts: 90
Zbarcam SIGSEGV Error
« on: July 24, 2017, 02:58:36 pm »
Hello Guys,

I would like to create a "live" barcode decoder app which use a webcam. I downloaded Zbar and based on the c example i created a simple app. When i push the button i get a SIGSEGV error. The funny thing is when i press play again in the IDE it's starts the camera and also decode the barcode. What can be the problem?

IDE: 1.6
FPC: 3.0

Code: Pascal  [Select][+][-]
  1. procedure TForm1.Button1Click(Sender: TObject);
  2.  var
  3.  processor : zbar_processor_t;
  4. begin
  5.   processor := zbar_processor_create(1); //With 0 it won't work at all
  6.   zbar_processor_set_config(processor, ZBAR_CODE39, ZBAR_CFG_ENABLE, 1); //I only need to decode CODE39
  7.   zbar_processor_init(processor, '/dev/video0', 1);
  8.   //zbar_processor_set_data_handler(processor, my_handler, nil); //I'll create a callback later :)
  9.   zbar_processor_set_visible(processor, 1);
  10.   zbar_processor_set_active(processor, 1);
  11. end;

Any Help welcome :).

Regards,
Sty

taazz

  • Hero Member
  • *****
  • Posts: 5368
Re: Zbarcam SIGSEGV Error
« Reply #1 on: July 24, 2017, 04:28:01 pm »
Knowing nothing about zbar and how it is used I have 2 general observations.
1) the posted code does not have all the information needed, add the declaration of the external procedures as well.
2) there is a zxing port for delphi in github that might be easier for you to use since it does not require any external dlls but it requires your own webcamera capture to image routines.
Good judgement is the result of experience … Experience is the result of bad judgement.

OS : Windows 7 64 bit
Laz: Lazarus 1.4.4 FPC 2.6.4 i386-win32-win32/win64

Stygian

  • Jr. Member
  • **
  • Posts: 90
Re: Zbarcam SIGSEGV Error
« Reply #2 on: July 25, 2017, 09:36:23 am »
Dear taazz,

All the external procedures can be found in the attached file.

I also tried zxing, but it's a pain to convert it properly from Delphi to Lazarus, cause ZXing 3.0 uses FMX in almost all example.
I downloaded the .net version client and it's looks good, but the lazarus version of ZXing what i found was 2D Barcodes, and I need 1D ones.

Regards,
Sty.

Thaddy

  • Hero Member
  • *****
  • Posts: 14165
  • Probably until I exterminate Putin.
Re: Zbarcam SIGSEGV Error
« Reply #3 on: July 25, 2017, 09:52:03 am »
That attached unit is for windows, not for linux.... So won't work. If it is avaliable for nixes I can probably fix it, but you have to provide a site where to download the libraries.
Code: Pascal  [Select][+][-]
  1. unit zbar;
  2. {$mode delphi}{$H+}
  3. interface
  4.  
  5. {$MINENUMSIZE 4}
  6.  
  7. uses
  8.   Windows, SysUtils, Classes {, dbc, DLL96V1, DLLSP96};

And this is unix:
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, '/dev/video0', 1);

« Last Edit: July 25, 2017, 09:55:39 am by Thaddy »
Specialize a type, not a var.

Stygian

  • Jr. Member
  • **
  • Posts: 90
Re: Zbarcam SIGSEGV Error
« Reply #4 on: July 25, 2017, 09:54:37 am »
Dear Thaddy,

Forget to mention, I use Windows 10 OS.

Regards,
Sty.

Thaddy

  • Hero Member
  • *****
  • Posts: 14165
  • Probably until I exterminate Putin.
Re: Zbarcam SIGSEGV Error
« Reply #5 on: July 25, 2017, 09:57:17 am »
And this is unix:
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, '/dev/video0', 1);

What do you mean? You say you are using windows, but try to open a unix device file? Either way that won't work! <grumpy  >:D >:D>

You have to give us *a lot* more information....

Maybe this works on windows, just a guess:
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, getdc(0){or simply 0}, 1);
And everything external needs to be declared as stdcall if windows and cdecl if otherwise. That header is a BAD translation. There's just cdecl. Which probably means UNIX. And that is also wrong because that needs to be done in the interface section and not (just) in the implementation section. <sigh>

Where did you get it from and where can I get a windows dll?
« Last Edit: July 25, 2017, 10:11:04 am by Thaddy »
Specialize a type, not a var.

Stygian

  • Jr. Member
  • **
  • Posts: 90
Re: Zbarcam SIGSEGV Error
« Reply #6 on: July 25, 2017, 10:40:31 am »
Dear Thaddy,

The dlls are from the original Zbar installer. The Zbar.pas comes from: ftp://ftp.lnssoftware.ca/Delphi/zbar.pas

Regards,
Sty.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: Zbarcam SIGSEGV Error
« Reply #7 on: July 25, 2017, 10:49:07 am »
zbar header.

Code: C  [Select][+][-]
  1. 750     /** constructor.
  2. 751      * if threaded is set and threading is available the processor
  3. 752      * will spawn threads where appropriate to avoid blocking and
  4. 753      * improve responsiveness
  5. 754      */
  6. 755     extern zbar_processor_t *zbar_processor_create(int threaded);
  7.  

Thaddy

  • Hero Member
  • *****
  • Posts: 14165
  • Probably until I exterminate Putin.
Re: Zbarcam SIGSEGV Error
« Reply #8 on: July 25, 2017, 10:53:22 am »
molly, IsMultithreaded=true is not enough. I am interested in solving this, but again: what is that unix code doing there? And why the cdecl for a windows dll that I can't find yet? And why are the declares not in the interface section? (you did not test it too, I can't, I am stupid and need more information  8-) )
And this is unix:
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, '/dev/video0', 1);
« Last Edit: July 25, 2017, 11:00:02 am by Thaddy »
Specialize a type, not a var.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: Zbarcam SIGSEGV Error
« Reply #9 on: July 25, 2017, 11:14:57 am »
molly, IsMultithreaded=true is not enough.
The library takes care of the threading.

Quote
I am interested in solving this, but again: what is that unix code doing there?
In case you must know:
Code: C  [Select][+][-]
  1. zbar_processor_t *zbar_processor_create (int threaded)
  2. {
  3.     zbar_processor_t *proc = calloc(1, sizeof(zbar_processor_t));
  4.     if(!proc)
  5.         return(NULL);
  6.     err_init(&proc->err, ZBAR_MOD_PROCESSOR);
  7.  
  8.     proc->scanner = zbar_image_scanner_create();
  9.     if(!proc->scanner) {
  10.         free(proc);
  11.         return(NULL);
  12.     }
  13.  
  14.     proc->threaded = !_zbar_mutex_init(&proc->mutex) && threaded;
  15.     _zbar_processor_init(proc);
  16.     return(proc);
  17. }
  18.  

Quote
And why the cdecl for a windows dll that I can't find yet?
You are referring to the Delphi header ? No, idea. Assuming it is defined as such in the sources of zbar to use specific calling convention ?

Quote
And why are the declares not in the interface section?
They are. It compiles fine for me. Custom dynamic loading.

Quote
(you did not test it too, I can't, I am stupid and need more information  8-) )
I never use 3th party headers from untrusted source  :P

Quote
And this is unix:
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, '/dev/video0', 1);
[/code]
That's a tougher one...
Code: C  [Select][+][-]
  1. int zbar_processor_init (zbar_processor_t *proc,
  2.                          const char *dev,
  3.                          int enable_display)
  4. {
  5.     if(proc->video)
  6.         zbar_processor_set_active(proc, 0);
  7.  
  8.     if(proc->window && !proc->input_thread.started)
  9.         _zbar_processor_close(proc);
  10.  
  11.     _zbar_mutex_lock(&proc->mutex);
  12.     _zbar_thread_stop(&proc->input_thread, &proc->mutex);
  13.     _zbar_thread_stop(&proc->video_thread, &proc->mutex);
  14.  
  15.     _zbar_processor_lock(proc);
  16.     _zbar_mutex_unlock(&proc->mutex);
  17.  
  18.     if(proc->window) {
  19.         zbar_window_destroy(proc->window);
  20.         proc->window = NULL;
  21.     }
  22.  
  23.     int rc = 0;
  24.     if(proc->video) {
  25.         zbar_video_destroy(proc->video);
  26.         proc->video = NULL;
  27.     }
  28.  
  29.     if(!dev && !enable_display)
  30.         /* nothing to do */
  31.         goto done;
  32.  
  33.     if(enable_display) {
  34.         proc->window = zbar_window_create();
  35.         if(!proc->window) {
  36.             rc = err_capture(proc, SEV_FATAL, ZBAR_ERR_NOMEM,
  37.                              __func__, "allocating window resources");
  38.             goto done;
  39.         }
  40.     }
  41.  
  42.     if(dev) {
  43.         proc->video = zbar_video_create();
  44.         if(!proc->video) {
  45.             rc = err_capture(proc, SEV_FATAL, ZBAR_ERR_NOMEM,
  46.                              __func__, "allocating video resources");
  47.             goto done;
  48.         }
  49.         if(proc->req_width || proc->req_height)
  50.             zbar_video_request_size(proc->video,
  51.                                      proc->req_width, proc->req_height);
  52.         if(proc->req_intf)
  53.             zbar_video_request_interface(proc->video, proc->req_intf);
  54.         if((proc->req_iomode &&
  55.             zbar_video_request_iomode(proc->video, proc->req_iomode)) ||
  56.            zbar_video_open(proc->video, dev)) {
  57.             rc = err_copy(proc, proc->video);
  58.             goto done;
  59.         }
  60.     }
  61.  
  62.     /* spawn blocking video thread */
  63.     int video_threaded = (proc->threaded && proc->video &&
  64.                           zbar_video_get_fd(proc->video) < 0);
  65.     if(video_threaded &&
  66.        _zbar_thread_start(&proc->video_thread, proc_video_thread, proc,
  67.                           &proc->mutex)) {
  68.         rc = err_capture(proc, SEV_ERROR, ZBAR_ERR_SYSTEM, __func__,
  69.                          "spawning video thread");
  70.         goto done;
  71.     }
  72.  
  73.     /* spawn input monitor thread */
  74.     int input_threaded = (proc->threaded &&
  75.                           (proc->window ||
  76.                            (proc->video && !video_threaded)));
  77.     if(input_threaded &&
  78.        _zbar_thread_start(&proc->input_thread, proc_input_thread, proc,
  79.                           &proc->mutex)) {
  80.         rc = err_capture(proc, SEV_ERROR, ZBAR_ERR_SYSTEM, __func__,
  81.                          "spawning input thread");
  82.         goto done;
  83.     }
  84.  
  85.     if(proc->window && !input_threaded &&
  86.        (rc = proc_open(proc)))
  87.         goto done;
  88.  
  89.     if(proc->video && proc->force_input) {
  90.         if(zbar_video_init(proc->video, proc->force_input))
  91.             rc = err_copy(proc, proc->video);
  92.     }
  93.     else if(proc->video) {
  94.         int retry = -1;
  95.         if(proc->window) {
  96.             retry = zbar_negotiate_format(proc->video, proc->window);
  97.             if(retry)
  98.                 fprintf(stderr,
  99.                         "WARNING: no compatible input to output format\n"
  100.                         "...trying again with output disabled\n");
  101.         }
  102.         if(retry)
  103.             retry = zbar_negotiate_format(proc->video, NULL);
  104.  
  105.         if(retry) {
  106.             zprintf(1, "ERROR: no compatible %s format\n",
  107.                     (proc->video) ? "video input" : "window output");
  108.             rc = err_capture(proc, SEV_ERROR, ZBAR_ERR_UNSUPPORTED,
  109.                              __func__, "no compatible image format");
  110.         }
  111.     }
  112.  
  113.  done:
  114.     _zbar_mutex_lock(&proc->mutex);
  115.     proc_leave(proc);
  116.     return(rc);
  117. }
  118.  
but,. the windows version seems to read:
Code: C  [Select][+][-]
  1. int _zbar_processor_init (zbar_processor_t *proc)
  2. {
  3.     return(0);
  4. }
  5.  
Should be doable ?

Downloads are from sf, here.
« Last Edit: July 25, 2017, 11:16:39 am by molly »

Thaddy

  • Hero Member
  • *****
  • Posts: 14165
  • Probably until I exterminate Putin.
Re: Zbarcam SIGSEGV Error
« Reply #10 on: July 25, 2017, 12:06:46 pm »
molly, IsMultithreaded=true is not enough.
The library takes care of the threading.
Not if FPC doesn't know about it. Can cause problems.
Quote
I am interested in solving this, but again: what is that unix code doing there?
Quote
In case you must know:
Code: C  [Select][+][-]
  1. zbar_processor_t *zbar_processor_create (int threaded)
  2. {
  3.     zbar_processor_t *proc = calloc(1, sizeof(zbar_processor_t));
  4.  
Calloc == stack alloc....

But if I have all the information it should be doable...
As long as zbar_processor_t is a locally declared record, skip the pointer. (if you want the whole thing in pascal)

If it compiles for you, does it actually work? then the problem is solved.
« Last Edit: July 25, 2017, 12:16:24 pm by Thaddy »
Specialize a type, not a var.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: Zbarcam SIGSEGV Error
« Reply #11 on: July 25, 2017, 12:22:07 pm »
Not if FPC doesn't know about it. Can cause problems.
Oh, you had me worried there for a moment but i understand. yes, afaik the structures are opaque except for the barcode-array.

If it compiles for you, does it actually work? then the problem is solved.
This very rudimentary test, compiles and works for me.

Code: Pascal  [Select][+][-]
  1. program test;
  2.  
  3. {$MODE OBJFPC}{$H+}
  4.  
  5. uses
  6.   SysUtils, StrUtils, zbar;
  7.  
  8. var
  9.   proc        : zbar_processor_t = nil;
  10.   use_threads : integer = 1;
  11.   use_window  : integer = 1;
  12.  
  13. procedure desert;
  14. begin
  15.   proc := zbar_processor_create(use_threads);
  16.  
  17.   if assigned(proc) then
  18.   begin
  19.     WriteLn(Format('created processor (%sthreaded)', [ifthen(use_threads > 0, 'un', '')]));
  20.  
  21.     if (zbar_processor_init(proc, nil, 0)) = 0 then
  22.     begin
  23.       WriteLn('initialized (video=disabled, window=disabled)');
  24.    
  25.     end
  26.     else WriteLn('unable to intialize processor');
  27.  
  28.     zbar_processor_destroy(proc);
  29.   end
  30.   else WriteLn('unable to create processor');
  31. end;
  32.  
  33.  
  34. var
  35.   ver_major: Cardinal;
  36.   ver_minor: Cardinal;
  37.  
  38. begin
  39.   if zbar_loaded then
  40.   begin
  41.     if zbar_version(ver_major, ver_minor) = 0 then
  42.     begin
  43.       WriteLn('libzbar version ', ver_major, '.', ver_minor);
  44.  
  45.       desert;
  46.     end
  47.     else writeln('unable to load version information');
  48.   end
  49.   else WriteLn('Unable to load libzbar dll');  
  50. end.
  51.  

Thaddy

  • Hero Member
  • *****
  • Posts: 14165
  • Probably until I exterminate Putin.
Re: Zbarcam SIGSEGV Error
« Reply #12 on: July 25, 2017, 01:04:03 pm »
So
Code: Pascal  [Select][+][-]
  1.   zbar_processor_init(processor, '/dev/video0', 1);
is legal?
Specialize a type, not a var.

molly

  • Hero Member
  • *****
  • Posts: 2330
Re: Zbarcam SIGSEGV Error
« Reply #13 on: July 25, 2017, 01:12:45 pm »
I highly doubt that the mentioned device is valid on a windows machine, e.g. the initialization of the processor fails in that case.

However, the example i'm (slowly) porting let me believe there is a way around providing an actual (video/output) device name. You can simply render in a window instead.

So, you are correct and TS' code-snippet is wrong in that regards.

edit: even in 2017 it is too fancy to not check return values, cross your fingers and hope for the best. Somehow these modern machines must be capable of recovering automatically from failing code  ;D
« Last Edit: July 25, 2017, 01:17:10 pm by molly »

 

TinyPortal © 2005-2018