SD870IS Firmware dumping - page 3 - Firmware Dumping - CHDK Forum

SD870IS Firmware dumping

  • 60 Replies
  • 30039 Views
*

Offline RyeBrye

  • **
  • 73
  • SD-870
Re: SD870IS Firmware dumping
« Reply #20 on: 19 / January / 2008, 23:55:49 »
Advertisements
I think my next step is going to be to write a function to step through pretty much the entire damned memory on this camera looking for the AF LED...  Having the blue LED will help tremendously in this process because we can have it blink patterns to indicate where it is in the scanning process to help avoid going crazy...

Here's what I was thinking would make sense to write a function to do:

For (i = 0 to big number, incrementing by 1) {
     Try to blink an LED at address at that step value (i.e. increment counter by one, but increment LED address by appropriate number of bytes)
     Wait a few seconds
     Blink the blue LED with a pattern indicating which one was just blinked
}

The function to blink the blue LED could be done in binary... with a 1-second window for each blip.

Before blinking out a number - have it blink rapidly 4 times in one second- and then pause for a second...

Blink once in the one second window - logical 1
Blink twice in the one second window - logical 0

we could put a pause of 0.125 seconds in between each bit just to help prevent a string of a lot of zeroes becoming hard to count...

Or... we could just do it morse-code style and do dots and dashes with some kind of flicker at the beginning to indicate it is starting a new number.

The benefit of reading it out in binary is that it would be easy to be human readable with a relatively constant time to read out each bit... If we had something where it blinked it out in base-10, that would be a pain in the butt to sit there and count... With the binary output you could just jot down things on paper and then if you missed it... just jot down the next one

Maybe this is overkill, but I think that leveraging the existing blue LED to find the AF LED would be a good use of our time. Unless, of course, someone can find my a blue-sensitive phototransistor... I know they must exist, I just can't find them. (Blue LEDs are in the 450 to 470 nm range for light). I'm willing to buy one and ship it out here, but even then if we could find the AF LED we could have the firmware dumped before the phototransistor would get here.

On another note - can the LED backlight be flickered at a fast enough speed to dump the firmware? I know it would be a big battery drain, but if any of us have phototransistors that could be sensitive to that moreso than the blue - that might be a good approach. That one is in a known range at least...

Anyway... those are my thoughts for now. What do the rest of you think?


« Last Edit: 20 / January / 2008, 00:00:09 by RyeBrye »

Re: SD870IS Firmware dumping
« Reply #21 on: 20 / January / 2008, 01:02:26 »
Sounds like a good approach, but I'd be worried about hitting something in flash accidentally by stepping through the memory. Since I don't know this architecture very well, I don't even know if this is a possibility, but nevertheless, I promised my wife I wouldn't do anything to the camera that had a chance of messing it up until its past warranty :-)

Something that has me wondering is the possibility of finding some way to use the video/audio output as data or GPIO. Also, the 5th pin (actually the 4th pin from the left as looking at the connector) in a mini-USB can sometimes be connected as a GPIO pin. I don't know for sure how Canon has it wired.

I know there are detectors sensitive to blue (probably UV also) but it just seems like overkill to have to overnight stuff from Digi-Key for this.
« Last Edit: 20 / January / 2008, 01:09:42 by Lobo »

*

Offline intrinsic

  • *
  • 29
  • S5IS
Re: SD870IS Firmware dumping
« Reply #22 on: 20 / January / 2008, 08:19:48 »
I think my next step is going to be to write a function to step through pretty much the entire damned memory on this camera looking for the AF LED...  Having the blue LED will help tremendously in this process because we can have it blink patterns to indicate where it is in the scanning process to help avoid going crazy...

There is code available which cycles through the addresses for determining LED locations, it is available here;
http://forums.dpreview.com/forums/read.asp?forum=1010&message=24988142

edit:
Code: [Select]
Forum  Canon Talk
Subject  Re: CHDK for A570IS - GOOD NEWS
Posted by  rossig  [CLICK FOR PROFILE]
Date/Time  12:08:31 PM, Thursday, September 27, 2007 (GMT)

Finally I was able to light my camera leds.

Using G7 blinker posted yesterday I tried to cycle through memory locations using the following modified main.c
#define DEL 1260

long* led;

void on(void){
 *led=0x46;
}

void off(void){
 *led=0x44;
}

void delay(int i){
 while(--i) {
  asm("nop\n");
  asm("nop\n");
 }
}

void send_byte(char b){
 char i;
 off();
 delay(DEL);
 for (i=0;i<8;i++){
  if (b&1) on(); else off();
  b>>=1;
  delay(DEL);
 }
 on();
 delay(DEL*3);
}

//void send_string(char* s){
// while(*s) send_byte(*s++);
//}


int i;
char *p;

int main(){
long ciclo;
for (ciclo=0xC0220060; ciclo<=0xC02200FF; ciclo++)
{
led=(long*)ciclo;
// p=(char*)0xFF800000; // 0xFFA00000 for secons part
 on();
 for (i=0;i<512;i++) send_byte(0x55);
 send_byte('b');
 send_byte('e');
 send_byte('g');
 send_byte('i');
 send_byte('n');
// for(i=0;i<0x200000;i++) send_byte(*p++);
 send_byte('e');
 send_byte('n');
 send_byte('d');
 send_byte('.');
 off();
 }
 return 0;
}


After a few seconds (20-30) every led of my camera lits in turn even AF_LED.

Now narrowing the cycling interval I think will be easy to obtain the exact memory location of mapped i/o port.

This weekend i will attempt to dump the firmware using original Grand blinker or G7 blinker with the right led memory loction.
EDIT: After 40-60 Sec
« Last Edit: 20 / January / 2008, 08:59:03 by acseven »

*

Offline RyeBrye

  • **
  • 73
  • SD-870
Re: SD870IS Firmware dumping
« Reply #23 on: 20 / January / 2008, 18:12:07 »
Thanks for that code... I was looking for that the other day but dpreview was hosed so I could get it.

I have modified it so that it will scan over the entire range specified, and output the loop variant after each step.

Code: [Select]
/**
 * SD870 blinker...
 * This code will scan through a set of addresses and will test each one
 * since the blue LED address is known, we use the blue LED to output the loop variant
 * after each step in binary using a "morse code" like system -
 * this will help nail it down once it blinks, you can jot down the loops dots and dashes...
 * (if you miss it, you can jot down the next one in the loop, and the one after that... etc)
 * to determine what step in the memory the LED lived at.
 *
 * Before each number is output for the loop variant, it will blip the blue LED once very quickly,
 * then pause, and then output the remainder in dots or dashes.
 **/

#define DEL 1260

#define DOT_DURATION        15000
#define DOT_PAUSE           90000
#define DASH_DURATION      180000
#define DASH_PAUSE          30000

#define NEW_NUMBER_PAUSE   300000

#define LED_BLUE 0xC02200CC

long* led;

void on(void){
 *led=0x46;
}

void off(void){
 *led=0x44;
}

void delay(int i){
 while(--i) {
  asm("nop\n");
  asm("nop\n");
 }
}

void blue_on(void) {
    volatile long *p;
    p=(void*)LED_BLUE;
    *p=0x46;
}
void blue_off(void) {
    volatile long *p;
    p=(void*)LED_BLUE;
    *p=0x44;
}
void blue_dot(void) {
    delay(DOT_PAUSE);
    blue_on();
    delay(DOT_DURATION);
    blue_off();
    delay(DOT_PAUSE);
}
void blue_dash(void) {
    delay(DASH_PAUSE);
    blue_on();
    delay(DASH_DURATION);
    blue_off();
    delay(DASH_PAUSE);
}

void blue_indicate_new(void) {
    delay(NEW_NUMBER_PAUSE);
   
    blue_on();
    delay(DASH_PAUSE);
    blue_off();
   
    delay(NEW_NUMBER_PAUSE);
}



void send_byte(char b){
 char i;
 off();
 delay(DEL);
 for (i=0;i<8;i++){
  if (b&1) on(); else off();
  b>>=1;
  delay(DEL);
 }
 on();
 delay(DEL*3);
}

void output_loop_var(int v) {
    blue_off();
    blue_indicate_new();
    int i;
    for (i=0;i<8;i++)  {
        if (v&1) blue_dash(); else blue_dot();
        v>>=1;
    }
}

//void send_string(char* s){
// while(*s) send_byte(*s++);
//}


int i;
char *p;

int main(){

long ciclo;
int c;
for (c=0; c <= 159; c++) {
    ciclo=0xC0220060+c;
    led=(long*)ciclo;
    // p=(char*)0xFF800000; // 0xFFA00000 for secons part
     on();
     for (i=0;i<512;i++) send_byte(0x55);
     send_byte('b');
     send_byte('e');
     send_byte('g');
     send_byte('i');
     send_byte('n');
    // for(i=0;i<0x200000;i++) send_byte(*p++);
     send_byte('e');
     send_byte('n');
     send_byte('d');
     send_byte('.');
     off();
output_loop_var(c);
 }
 return 0;
}


I've got my camera scanning through it... the flash fires and the LCD backlight definitely flickers a lot at part of that range... I jotted down the dots and dashes - but I think I might redo that so I don't have to be a morse-code expert to read it... or I might get my other camera down here so I can record it and play it back later so it's easier to decode :)

There is definitely a tradeoff at work here... I want each loop variant to output fast enough to not make the camera take forever to scan the addresses, but I also want to be able to decode it if I need to...

The LCD backlight is hella bright, I think that one could possibly be useful for dumping. Has anyone ever used the backlight LED for a dump before?
« Last Edit: 20 / January / 2008, 18:13:52 by RyeBrye »

*

Offline RyeBrye

  • **
  • 73
  • SD-870
Re: SD870IS Firmware dumping
« Reply #24 on: 20 / January / 2008, 22:31:19 »
Good news. Found the bicolor LED and looks like more will come soon... Here's the code I'm using: it blinks decimals now (short dot for a zero, then counts out each decimal - hundreds first, then 10's then 1's)

Code: [Select]
/**
 * SD870 blinker...
 * This code will scan through a set of addresses and will test each one
 * since the blue LED address is known, we use the blue LED to output the loop variant
 * after each step in binary using a "morse code" like system -
 * this will help nail it down once it blinks, you can jot down the loops dots and dashes...
 * (if you miss it, you can jot down the next one in the loop, and the one after that... etc)
 * to determine what step in the memory the LED lived at.
 *
 * Before each number is output for the loop variant, it will blip the blue LED once very quickly,
 * then pause, and then output the remainder in dots or dashes.
 **/

#define DEL 1260

#define DOT_DURATION         5000
#define DOT_PAUSE          150000
#define DASH_DURATION      150000
#define DASH_PAUSE          50000

#define NEW_NUMBER_PAUSE   600000

#define LED_BLUE 0xC02200CC

#define OUTPUT_DECIMAL 1

long* led;

void on(void){
 *led=0x46;
}

void off(void){
 *led=0x44;
}

void delay(int i){
 while(--i) {
  asm("nop\n");
  asm("nop\n");
 }
}

void blue_on(void) {
    volatile long *p;
    p=(void*)LED_BLUE;
    *p=0x46;
}
void blue_off(void) {
    volatile long *p;
    p=(void*)LED_BLUE;
    *p=0x44;
}
void blue_dot(void) {
    delay(DOT_PAUSE);
    blue_on();
    delay(DOT_DURATION);
blue_off();
}
void blue_dash(void) {
    delay(DASH_PAUSE);
    blue_on();
    delay(DASH_DURATION);
    blue_off();
}

void blue_indicate_new(void) {
    delay(NEW_NUMBER_PAUSE);
}



void send_byte(char b){
 char i;
 off();
 delay(DEL);
 for (i=0;i<8;i++){
  if (b&1) on(); else off();
  b>>=1;
  delay(DEL);
 }
 on();
 delay(DEL*3);
}

#ifdef OUTPUT_DECIMAL
void output_decimal_number(int d) {
if (d>0) {
int i;
     for (i=0;i<d;i++)  {
blue_dash();
    }
}
else {
blue_dot();
}
delay(NEW_NUMBER_PAUSE);
}

void output_loop_var(int n) {
    blue_off();
    blue_indicate_new();
 int ones = (n >= 10) ? n%10 : n;
       n /= 10;
       int tens = ( n >= 10 ) ? n%10 : n;
       n /= 10;
       int hundreds = ( n >= 10 ) ? n%10 : n;

/*    int hundreds = (n >= 100) ? n/100 : 0;
    n -= hundreds*100;
    int tens = ( n >= 10 ) ? n/10 : 0;
    n -= tens*10;
    int ones = ( n >= 0 ) ? n : 0; */

output_decimal_number(hundreds);
output_decimal_number(tens);
output_decimal_number(ones);

}
#else
void output_loop_var(int v) {
    blue_off();
    blue_indicate_new();
    int i;
    for (i=0;i<8;i++)  {
        if (v&1) blue_dash(); else blue_dot();
        v>>=1;
    }
}
#endif


//void send_string(char* s){
// while(*s) send_byte(*s++);
//}


int i;
char *p;

int main(){
#ifdef TEST_NUMBER_OUTPUT
output_loop_var(1);
delay(NEW_NUMBER_PAUSE);
output_loop_var(10);
delay(NEW_NUMBER_PAUSE);
output_loop_var(100);
delay(NEW_NUMBER_PAUSE);
output_loop_var(121);
delay(NEW_NUMBER_PAUSE);
output_loop_var(32);
delay(NEW_NUMBER_PAUSE);
output_loop_var(12);
#endif
long ciclo;
int c;
// for the range from 0xC0220060 to 0xC02200FF
// scan from c=to to c=159 and start at 0xC0220060
// In my case, I'm reverse scanning from
// 0xC022013B and going backwards for 219 addresses
 
for (c=0; c <= 219; c++) {

    ciclo=0xC022013B-c;

    led=(long*)ciclo;
    // p=(char*)0xFF800000; // 0xFFA00000 for secons part
     on();
     for (i=0;i<512;i++) send_byte(0x55);
     send_byte('b');
     send_byte('e');
     send_byte('g');
     send_byte('i');
     send_byte('n');
    // for(i=0;i<0x200000;i++) send_byte(*p++);
     send_byte('e');
     send_byte('n');
     send_byte('d');
     send_byte('.');
     off();
output_loop_var(c);
 }

 return 0;
}

The code blinked out 4 after the green LED, and 5 also - it turns orange colored at 5, 6, 7, and it turns red at 8 9 10...

So this one LED has a few addresses corresponding to it, it would seem.

Green: 0xC0220136
Orange: 0xC0220135 or 0xC0220134
Redish: 0xC0220132 or 0xC0220131 or 0xC0220130

EDIT - I don't know if the redish was the same as the orange or not... but in trying to get it to work by itself I can only get orange and green... Here are addresses that work for both those colors:

 LED_BLUE   0xC02200CC
 LED_GREEN  0xC0220136
 LED_ORANGE  0xC0220133

I'm starting at 0xC022013B and working backwards... I'll post if I find any more LEDs - if someone else wants to confirm those values and see if their phototransistor works on the orange state of the bi-colored LED that might be a good idea :)

I suppose now that I have one LED that does 3 colors, I could rewrite the output to use the green as 1's the orange as 10's and the red as 100's and not have to have any of the dots for zero... maybe I will when I get through this scan if I haven't found the AF beam LED yet.

(as much fun as this is... I think getting the dump is more fun!)
« Last Edit: 20 / January / 2008, 23:59:34 by RyeBrye »

*

Offline RyeBrye

  • **
  • 73
  • SD-870
The HUNT for the AF LED
« Reply #25 on: 21 / January / 2008, 00:29:48 »
Ok... If any SD870 owners want to help hunt for the AF LED, I've made it really really easy...

Code: [Select]
/**
 * SD870 blinker...
 * - the hunt for the AF LED...
 *
 * Set three things, then compile and run...
 * #1 - Set the starting memory address,
 * #2 - The increment (1, or to scan backwards, -1)
 * #3 - Number of values to scan
 *
 * As it runs, after each LED it tries, it will output the number in the counter.
 * - One hundreds are output orange, tens are output on the blue LED, and 1's are output on the green LED
 *   (the ping pong nature of the different LEDs makes it easy to keep track of which number is which...)
 *
 * When it first runs, it will output 333 - just to help you identify the LEDS at work, and to let you know it is working
 * - as you scan through, when you find something of interest, look to see what the counter increment is.
 *
 * Add or subtract this from your starting value, and you have the memory address of the LED you just found!
 *  (google helps a lot - just put in something like "0xC022015C + 32" and it will spit out the hex address for you)
 *
 * If you find the AF LED - scream Eureka, strip off your clothes, and run to post it on the net
 *
 * Modified scanning method written by RyeBrye to output the counter increments...
 **/

#define STARTING_ADDRESS 0xC0220060
#define INCREMENT        1
#define NUM_TO_SCAN         169

#define DEL 1260

#define DOT_DURATION         5000
#define DOT_PAUSE          150000
#define DASH_DURATION      150000
#define DASH_PAUSE          50000

#define NEW_NUMBER_PAUSE   600000

#define LED_BLUE   0xC02200CC
#define LED_GREEN  0xC0220136
#define LED_ORANGE  0xC0220133
// this address isn't quite working
#define LED_RED    0xC0220130

#define OUTPUT_DECIMAL 1
#undef TEST_NUMBER_OUTPUT

long* led;

void on(void){
 *led=0x46;
}

void off(void){
 *led=0x44;
}

void delay(int i){
 while(--i) {
  asm("nop\n");
  asm("nop\n");
 }
}

void led_on(long led_addr) {
    volatile long *p;
    p=(void*)led_addr;
    *p=0x46;
}
void led_off(long led_addr) {
    volatile long *p;
    p=(void*)led_addr;
    *p=0x44;
}
void output_dot(long led_addr) {
    delay(DOT_PAUSE);
    led_on(led_addr);
    delay(DOT_DURATION);
led_off(led_addr);
}
void output_dash(long led_addr) {
    delay(DASH_PAUSE);
    led_on(led_addr);
    delay(DASH_DURATION);
    led_off(led_addr);
}

void blue_indicate_new(void) {
    delay(NEW_NUMBER_PAUSE);
}



void send_byte(char b){
 char i;
 off();
 delay(DEL);
 for (i=0;i<8;i++){
  if (b&1) on(); else off();
  b>>=1;
  delay(DEL);
 }
 on();
 delay(DEL*3);
}

#ifdef OUTPUT_DECIMAL
void output_decimal_number(int d, long led_addr) {
if (d>0) {
int i;
     for (i=0;i<d;i++)  {
output_dash(led_addr);
    }
}
else {
// output_dot(led_addr);
}
//delay(NEW_NUMBER_PAUSE);
}

void output_loop_var(int n) {
    //blue_off();
   // blue_indicate_new();
 int ones = (n >= 10) ? n%10 : n;
       n /= 10;
       int tens = ( n >= 10 ) ? n%10 : n;
       n /= 10;
       int hundreds = ( n >= 10 ) ? n%10 : n;

/*    int hundreds = (n >= 100) ? n/100 : 0;
    n -= hundreds*100;
    int tens = ( n >= 10 ) ? n/10 : 0;
    n -= tens*10;
    int ones = ( n >= 0 ) ? n : 0; */
if (hundreds > 0)
output_decimal_number(hundreds, LED_ORANGE );
if (tens > 0)
output_decimal_number(tens, LED_BLUE );
if (ones > 0)
output_decimal_number(ones, LED_GREEN);

}
#else
void output_loop_var(int v) {
    blue_off();
    blue_indicate_new();
    int i;
    for (i=0;i<8;i++)  {
        if (v&1) blue_dash(); else blue_dot();
        v>>=1;
    }
}
#endif


//void send_string(char* s){
// while(*s) send_byte(*s++);
//}


int i;
char *p;

int main(){
#ifdef TEST_NUMBER_OUTPUT
output_loop_var(333);
delay(NEW_NUMBER_PAUSE);
output_loop_var(321);
delay(NEW_NUMBER_PAUSE);
output_loop_var(123);
delay(NEW_NUMBER_PAUSE);
output_loop_var(1);
delay(NEW_NUMBER_PAUSE);
output_loop_var(10);
delay(NEW_NUMBER_PAUSE);
output_loop_var(100);
delay(NEW_NUMBER_PAUSE);
output_loop_var(121);
delay(NEW_NUMBER_PAUSE);
output_loop_var(32);
delay(NEW_NUMBER_PAUSE);
output_loop_var(12);
#endif
long ciclo;
int c;
// for the range from 0xC0220060 to 0xC02200FF
// scan from c=to to c=159 and start at 0xC0220060
// In my case, I'm reverse scanning from
// 0xC022013B and going backwards for 219 addresses

// quick output to prove the camera is working...
output_loop_var(333);
for (c=INCREMENT; abs(c) <= NUM_TO_SCAN; c += INCREMENT) {

    ciclo=STARTING_ADDRESS+c;

    led=(long*)ciclo;

     on();
     for (i=0;i<512;i++) send_byte(0x55);
     send_byte('b');
     send_byte('e');
     send_byte('g');
     send_byte('i');
     send_byte('n');
   
     send_byte('e');
     send_byte('n');
     send_byte('d');
     send_byte('.');
     off();
     output_loop_var(abs(c));
 }
 led_on(LED_BLUE);

 return 0;
}

All you need to do is follow the instructions in that main.c file - pick a starting address, pick a direction to go, and then let it rip... Each counter increment it output using the LEDs we have already found.

I've scanned a lot of the lower values that the other scanning loop had, but I'm focusing on moving into higher values now... Although I'm also doing other stuff while I do this so there is a chance that the AF LED has gone off but I didn't notice it... so it's probably helpful if we have a few people try to scan the different memory areas...

The defaults in the above are the same as the scanning file for the G7... So you can either run that one to get your feet wet (and make note when you find the LED backlight and the flash - just for kicks) - or you can pick a different region and see if you can find that stupid AF LED...

Although - maybe the orange LED is good enough too... someone can try a dump with that LED

UPDATE: I fixed a major flaw I had in the code today (Monday 12 noon MDT) - the starting address variable was set but not being used... woops!  :-[ It will NOW scan through starting at what you specify and cover the addresses you specify... etc.

« Last Edit: 21 / January / 2008, 14:56:50 by RyeBrye »

Re: SD870IS Firmware dumping
« Reply #26 on: 21 / January / 2008, 00:32:18 »
Nice RyeBrye  ! Good move !

Re: SD870IS Firmware dumping
« Reply #27 on: 21 / January / 2008, 00:35:36 »
RyeBrye ... you should try with the orange led .. I'm almost sure the sensitivity is high enough at this wavelenght.

*

Offline RyeBrye

  • **
  • 73
  • SD-870
Re: SD870IS Firmware dumping
« Reply #28 on: 21 / January / 2008, 00:43:33 »
RyeBrye ... you should try with the orange led .. I'm almost sure the sensitivity is high enough at this wavelenght.

Yeah, it probably would be - but I don't know if my phototransistor is any good or not :) After I get through scanning this region (about 100 more to go...) I'll see if I can get it to register anything.

The nice thing about the scanner thing is I can just leave it going and have the AF LED in my peripheral vision... if that LED or the LED on top ever fires - I can then just pick it up and count the blinks on the back and *bam* - got the LED address...

Of course, since a phototransistor that would be blue sensitive + shipping to get it out to me would be about $5 - I guess I just proved my time was only worth $2.50 / hour  :lol (better not tell my office about this!)

UPDATE: The phototransistor I have is good for IR, but not much else... so I'll continue to have the camera run through some different areas of memory looking to see if I can find the AF LED today.. I connected it to my audio in and got noise for everything I tried - but got a nice signal when I fired an IR remote at it - which leads me to believe that it's only sensitive to IR. So... I can either use the AF LED or get another phototransistor... and since I've got work to do today, and it's easy to let the camera sit and scan through memory addresses - I'll just do that throughout the day and see if I can get lucky.
« Last Edit: 21 / January / 2008, 13:11:57 by RyeBrye »

*

Offline RyeBrye

  • **
  • 73
  • SD-870
Re: SD870IS Firmware dumping
« Reply #29 on: 21 / January / 2008, 23:41:55 »
I FOUND THE AF LED
#define LED_AF      0xC0223030  :haha  :haha  :haha

Yeah... It took a lot of scanning to find it... I eventually wrote a "blast scanner" to scan through 0x100 regions at a time, turning them all on (and leaving them all on) and then just marched up the memory until I found the location... I discovered that if you scan too fast - the camera will simply shut itself off... (perhaps you draw too much power at once if the flash and 5 LEDs light at once?).

I never did find the power LED... and no... I'm not going to keep looking just to "complete the set" :)

Oh... and yes... I expect applause or karma or something :)

Now... I'll start dumping - but everyone else should be able to dump too... and since I have to actually do real work tomorrow don't expect me to keep going at this marathon-pace :) (in other words... someone else's turn to take the lead for a while!)

This should be an interesting dump. I wonder if it's a bad sign when the AF LED is about 12081 memory addresses above the highest value routinely scanned for... Lets hope it's VxWorks and the only thing strange about it is the LED addresses... and that strange scroll wheel thing, but lets hope we don't have to muck with that to port CHDK to this bad boy)

I will post the code I used to find it - but with the following caveat: it's not super clean. It's pretty specific to this scenario, and if anyone wants to use pieces of it to scan a different camera that's fine - I'm just not willing to provide support for it because chances are I'll have long since forgotten what was going on...

That being said - here's the code I used to blast scan through the memory...
Code: [Select]
/**
 * SD870 blinker...
 * - the hunt for the AF LED...
 *
 * Set three things, then compile and run...
 * #1 - Set the starting memory address,
 * #2 - The increment (1, or to scan backwards, -1)
 * #3 - Number of values to scan
 *
 * As it runs, after each LED it tries, it will output the number in the counter.
 * - One hundreds are output orange, tens are output on the blue LED, and 1's are output on the green LED
 *   (the ping pong nature of the different LEDs makes it easy to keep track of which number is which...)
 *
 * When it first runs, it will output 333 - just to help you identify the LEDS at work, and to let you know it is working
 * - as you scan through, when you find something of interest, look to see what the counter increment is.
 *
 * Add or subtract this from your starting value, and you have the memory address of the LED you just found!
 *  (google helps a lot - just put in something like "0xC022015C + 32" and it will spit out the hex address for you)
 *
 * If you find the AF LED - scream Eureka, strip off your clothes, and run to post it on the net
 *
 * Modified scanning method written by RyeBrye to output the counter increments...
 **/

// NOTE - the above usage notes do not reflect the most current state of the camera-scanning code below.
// you should be able to figure out what it's doing if you just look it over a bit...


// Definitely scanned: 0xC02200FF to 0xC0220060 going backwards
// Found: Flash at -117 or -118, -119 LED backlight at around -112, -113, -114, -115
// (these map to: LED backlight: 0xC022008E, 0xC022008D or so Flash: 0xC022008A or 0xC0220089 )
//
// Scanning: 0xC0220060 to 0xC0220000 backwards
// Found: camera turned itself off after a few steps... 20?

// blast scanning... something between 0xC022004B and 0xC0220055 seems to turn it off
// 0xC0220210 turns off camera

/// Y/eSSSSSS!!!!!!! 34 - 35

#define STARTING_ADDRESS 0xC022302F
#define END_ADDRESS 0xC0230FFF
#define BLAST_SCAN 1
#define BLAST_MULTIPLE      1
#define INCREMENT      1
#define NUM_TO_SCAN     10
// try to avoid memory addresses we know are a flash
#define AVOID_FLASHES 1
// just turn on the LEDs - don't ever turn them off
#define TURN_ON_ONLY 1
#define BLAST_STEP_PAUSE      20000


#define DEL 1260

#define DOT_DURATION         5000
#define DOT_PAUSE          150000
#define DASH_DURATION      150000
#define DASH_PAUSE          50000

#define NEW_NUMBER_PAUSE   200000

#define LED_BLUE   0xC02200CC
#define LED_GREEN  0xC0220136
#define LED_ORANGE  0xC0220133
#define LED_AF 0xC0223030

#define FLASH_ONE 0xC022008A
#define FLASH_TWO 0xC0220089
#define FLASH_THREE 0xC0220088
#define FLASH_FOUR 0xC0220210

#define OUTPUT_DECIMAL 1
#undef TEST_NUMBER_OUTPUT 

long* led;

void on(void){
 *led=0x46;
}

void off(void){
 *led=0x44;
}

void delay(int i){
 while(--i) {
  asm("nop\n");
  asm("nop\n");
 }
}

void led_on(long led_addr) {
#ifdef AVOID_FLASHES
if (led_addr == FLASH_ONE || led_addr == FLASH_TWO || led_addr == FLASH_THREE || led_addr == FLASH_FOUR )
return;
    #endif
    volatile long *p;
    p=(void*)led_addr;
    *p=0x46;
}
void led_off(long led_addr) {
#ifdef AVOID_FLASHES
if (led_addr == FLASH_ONE || led_addr == FLASH_TWO || led_addr == FLASH_THREE || led_addr == FLASH_FOUR ) {
return;
}
else {
    #endif
    volatile long *p;
    p=(void*)led_addr;
    *p=0x44;
#ifdef AVOID_FLASHES
}
#endif

}
void output_dot(long led_addr) {
    delay(DOT_PAUSE);
    led_on(led_addr);
    delay(DOT_DURATION);
led_off(led_addr);
}
void output_dash(long led_addr) {
    delay(DASH_PAUSE);
    led_on(led_addr);
    delay(DASH_DURATION);
    led_off(led_addr);
}

void blue_indicate_new(void) {
    delay(NEW_NUMBER_PAUSE);
}



void send_byte(char b){
 char i;
 off();
 delay(DEL);
 for (i=0;i<8;i++){
  if (b&1) on(); else off();
  b>>=1;
  delay(DEL);
 }
 on();
 delay(DEL*3);
}

#ifdef OUTPUT_DECIMAL
void output_decimal_number(int d, long led_addr) {
if (d>0) {
int i;
     for (i=0;i<d;i++)  {
output_dash(led_addr);
    }
}
else {
// output_dot(led_addr);
}
//delay(NEW_NUMBER_PAUSE);
}

void output_loop_var(int n) {
    //blue_off();
   // blue_indicate_new();
 int ones = (n >= 10) ? n%10 : n;
       n /= 10;
       int tens = ( n >= 10 ) ? n%10 : n;
       n /= 10;
       int hundreds = ( n >= 10 ) ? n%10 : n;

/*    int hundreds = (n >= 100) ? n/100 : 0;
    n -= hundreds*100;
    int tens = ( n >= 10 ) ? n/10 : 0;
    n -= tens*10;
    int ones = ( n >= 0 ) ? n : 0; */
if (hundreds > 0)
output_decimal_number(hundreds, LED_ORANGE );
if (tens > 0)
output_decimal_number(tens, LED_BLUE );
if (ones > 0)
output_decimal_number(ones, LED_GREEN);

}
#else
void output_loop_var(int v) {
    blue_off();
    blue_indicate_new();
    int i;
    for (i=0;i<8;i++)  {
        if (v&1) blue_dash(); else blue_dot();
        v>>=1;
    }
}
#endif


//void send_string(char* s){
// while(*s) send_byte(*s++);
//}


int i;
char *p;

int main(){
#ifdef TEST_NUMBER_OUTPUT
output_loop_var(900);
output_loop_var(101);
output_loop_var(101);
output_loop_var(101);
output_loop_var(101);
output_loop_var(101);
output_loop_var(903);
output_loop_var(803);
output_loop_var(903);
output_loop_var(803);
delay(NEW_NUMBER_PAUSE);
output_loop_var(333);
delay(NEW_NUMBER_PAUSE);
output_loop_var(321);
delay(NEW_NUMBER_PAUSE);
output_loop_var(123);
delay(NEW_NUMBER_PAUSE);
output_loop_var(1);
delay(NEW_NUMBER_PAUSE);
output_loop_var(10);
delay(NEW_NUMBER_PAUSE);
output_loop_var(100);
delay(NEW_NUMBER_PAUSE);
output_loop_var(121);
delay(NEW_NUMBER_PAUSE);
output_loop_var(32);
delay(NEW_NUMBER_PAUSE);
output_loop_var(12);
#endif
long ciclo;
int c;
// for the range from 0xC0220060 to 0xC02200FF
// scan from c=to to c=159 and start at 0xC0220060
// In my case, I'm reverse scanning from
// 0xC022013B and going backwards for 219 addresses

// quick output to prove the camera is working...
output_loop_var(333);
#ifdef BLAST_SCAN
//ciclo = STARTING_ADDRESS;
int increment = (END_ADDRESS > STARTING_ADDRESS) ? 1 : -1;
int loopcount = 0;
for (ciclo=STARTING_ADDRESS; ((increment > 0) ? ( ciclo <= END_ADDRESS) : ( ciclo >= END_ADDRESS)) ; ciclo+=(BLAST_MULTIPLE*increment)) {
int blinkcount;
for (blinkcount=0; blinkcount<4; blinkcount++) {
int i;
for (i=0; i< BLAST_MULTIPLE; i++) {
led_on(ciclo+i);
delay(DEL*5);
}
delay(BLAST_STEP_PAUSE);
#ifndef TURN_ON_ONLY
delay(NEW_NUMBER_PAUSE);
for (i=0; i< BLAST_MULTIPLE; i++) {

led_off(ciclo+i);
}
#endif
}
loopcount++;
output_loop_var(abs(loopcount));
}
#else
for (c=0; abs(c) <= NUM_TO_SCAN; c += INCREMENT) {

    ciclo=STARTING_ADDRESS+c;

    led=(long*)ciclo;
     on();
led(long*)ciclo++;
     for (i=0;i<512;i++) send_byte(0x55);
     send_byte('b');
     send_byte('e');
     send_byte('g');
     send_byte('i');
     send_byte('n');
   
     send_byte('e');
     send_byte('n');
     send_byte('d');
     send_byte('.');
     off();
output_loop_var(abs(c));
 }
#endif
 led_on(LED_BLUE);

 return 0;
}

« Last Edit: 21 / January / 2008, 23:55:33 by RyeBrye »

 

Related Topics


SimplePortal © 2008-2014, SimplePortal