1

I'm writing code on the Macintosh in C++. Long story short, it's interfacing with TWAIN.

We coded against the TWAIN standard and with the main flatbed scanner we used to develop against, it works perfectly. With other scanners, not so much.

In particular, the second scanner I'm working with it tends to crash at random points and intervals.

For example, it will sometimes crash on a line like this

OSErr err = DSM_Entry(&mAppIdentity,
                      NULL, 
                      DG_CONTROL, 
                      DAT_IDENTITY, 
                      MSG_OPENDS, 
                      (TW_MEMREF)&mDSIdentity);

DSM_Entry is an aliased system call to a TWAIN function (I think that's the term).mDSIdentity and mAppIdentity are both TW_IDENTITY stuctures, a TWAIN thing. One of them identifies our app, the other is fetching the value of the data source (the TWAIN scanner). The DG_ arguments are an "operation triplet", they're #define values which, in this combination, represent a specific operation - in this case, opening a data source from the data source manager

And sometimes this works, and sometimes it fails. Sometimes it fails on the third scan, sometimes the second scan, and sometimes the first. Like I said in the first scanner it works great, in the others it dies at these random intervals.

In the debugger the message I see varies but one thing I usually see is EXC_BAD_ACCESS:

Program received signal:  “EXC_BAD_ACCESS”.
Cannot access memory at address 0x17f3ccac

Some amount of searching indicates that this tends to happen on Apple platforms (the iPhone and Obj-C is often what's hit) whenever something bad has happened with regards to memory, like maybe using a dereferenced pointer. Being memory related would seem to support the randomness but I can't figure out where it's going wrong, especially since there doesn't seem to be anything different from when it works versus when it doesn't (i.e., at a breakpoint at the exact DSM_Entry call that crashes the values appear to be identical to the very-similar DSM_Entry call just before it that worked fine), the memory locations of the variables involved do not match the memory address in the error, and DSM_Entry is supposed to return a code if it fails, but in this case it's just crashing everything, and exception handling has no effect.

I'm comforted somewhat by the fact that according to Apple developers, EXC_BAD_ACCESS and its ilk are the hardest errors to debug, but I'm not sure where to go with this. Since we're interfacing with TWAIN drivers which we didn't write, it could be that the error's not even in our code per se. This led me to ask about the state of TWAIN on the Mac (since we haven't had near this much trouble in Windows) but we've tested against at least four different scanner manufacturers and I have a hard time believing that they could all be wrong.

Also I'm compiling in Xcode with all of the warnings turned on and still getting no clues (or additional warnings) as to what's going on.

Does anyone have any additional advice for troubleshooting an EXEC_BAD_ACCESS error, or how to find out if it's even my code's fault?

Community
  • 1
  • 1
Tom Kidd
  • 12,830
  • 19
  • 89
  • 128
  • Can you isolate this into a small snippet of code to ensure that you get the same error there? This will help you figure out if the error is on your end or not. – Nathan S. Nov 04 '10 at 19:53
  • @Nathan S.: Not really. I mean, it always happens on one of these DSM_Entry calls (and due to the nature of communicating with TWAIN, there are numerous calls) but not always the same one and sometimes not at all. – Tom Kidd Nov 04 '10 at 20:05
  • I haven't used TWAIN myself, but what happens if you write a small program that just makes DSM_Entry calls, and doesn't handle any other data? If your program is small enough you can quickly verify that the problem must be in the API. Then you just have to find the magic work-around to get things working. I'd suggest asking on Apple's mailing lists if you haven't already. – Nathan S. Nov 04 '10 at 22:21

2 Answers2

1

If you run in GDB you should see a stacktrace which will give you some pretty good clues, though it won't tell you instantly if the problem is that you left bad stuff or not.

You could also try enabling malloc debugging.

bmargulies
  • 97,814
  • 39
  • 186
  • 310
  • Yeah I've been running in GDB and I'm getting no stack trace despite running it in debug mode, having it not strip symbols, etc. Which maybe lends some credence to it being a bug in someone else's code. Dunno. Thanks for the malloc debugging tip though, I'll try that out. – Tom Kidd Nov 04 '10 at 20:06
  • what do you mean 'no backtrace'. It doesn't stop, or it doesn't show anything interesting? – bmargulies Nov 04 '10 at 20:52
  • When the Xcode debugger is attached it stops cold at that point and all I get out of it is two lines like I've pasted above. No stack trace. If I'm not attached to the debugger the program just crashes. – Tom Kidd Nov 04 '10 at 21:47
  • I'd try it with gdb from command-level, myself, in case of xcode pranks. – bmargulies Nov 05 '10 at 01:27
0

I had the same issue, the application was crashing only when I was trying to open some scanners (MSG_OPENDS). When calling MSG_OPENDS on some scanners (usb), the application was allocating lots of memory which sometimes lead to a crash.

I've spent lots of time thinking it was a bug in the code, but when I tested the same code in TwainClientCocoa it was working well.

Finally, after wasting several more hours, I managed to fix it.. by setting the CFBundleIconFile from the project's plist.

When MSG_OPENDS fails, it shows an alert box which also contains the application icon. My guess is that the problem comes from that alert (bug either in Twain.framework.. or some other framework being used by Twain).

alex-i
  • 5,406
  • 2
  • 36
  • 56