EEVblog Electronics Community Forum

EEVblog => EEVblog Specific => Topic started by: EEVblog on November 05, 2018, 12:34:00 am

Title: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on November 05, 2018, 12:34:00 am
David looks at the pins on the Padauk PMS150 programmer for potential reverse engineering.

TLDR; It doesn't look easy to reverse engineer this protocol, it's messy with lots of voltage levels, as Padauk said it would be.
Just buy the programmer for now!
There is also a Flash/EEPROM re-programmable version of the chip, the PFS154C.

https://www.youtube.com/watch?v=4Zw_W0iaGFM (https://www.youtube.com/watch?v=4Zw_W0iaGFM)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: BrianHG on November 05, 2018, 01:02:01 am
Looks like the first generation PIC16C54 programming levels, with fewer active IOs.  The old PICs used to use half the IOs to be programmed with wacko voltage transients and some analog levels thrown in as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ataradov on November 05, 2018, 01:16:54 am
Voltage levels on I/Os are probably not important, they are just matching the supply voltage, but it would probably work fine as long as you cross the threshold.

Just use a logic analyzer to grab their logical level. Clamp it with diodes if needed, although I suspect that simple current limiting resistors will be sufficient.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 05, 2018, 02:53:26 am
Regarding the different voltage levels: Old EPROMs required this, too. For example some algorithms verified if it was programmed correctly at 6V and 4V. So might be that the highest voltage phase is the programming phase, and two other low voltage phases are verify, and maybe a normal voltage phase for reading the ID etc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Smokey on November 05, 2018, 05:33:43 am
Is anyone else a little confused by this?

Did I miss part of the video or something or did you not tell us how long the total programming time is? 
ms, seconds, tens of seconds?  That's kind of important to get an idea of the amount of data capture required.

Also did you intentionally grab the least capable data acquisition device possible?  We all know that lab is jam packed with high end gear that almost never gets used.  I'm pretty sure there are at least a couple multi-thousand-dollar deep memory 4 channel MSOs with real level triggering on the digital channels that should be more than capable.  I'm also pretty sure you can take the couple 4channel Keysight scopes sitting around, time correlate all the analog channels between scopes, and dump all that to a PC for a full time deep memory data dump.

It's one thing if you want to do some simple Arduino project video for beginners and don't want to scare viewers off by using test equipment they probably won't have.  It's another thing to do a real engineering project like reversing an uC programming procedure with only toy test equipment and then sound surprised when it didn't all just work out and you couldn't get all the data you needed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 05, 2018, 06:34:02 am
In a Youtube comment David said the big scopes are still all in boxes, because of their move.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Smokey on November 05, 2018, 07:17:14 am
In a Youtube comment David said the big scopes are still all in boxes, because of their move.

Ahhh.  Well that explains some things. 
It would be nice to put a big huge disclaimer at the beginning of the video that you actually know the equipment you are using is not the right tool for the job and will probably never have the capabilities to succeed and that you are really just playing.

Question:
Do you guys typically read the youtube comments?  Mark me as a "no".
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: westfw on November 05, 2018, 08:35:11 am
I think you can probably decide that the pins not present on the SOT-6 package (PA0 (7) and PA7 (2)) are not particularly relevant to the programming spec...  (the programmer may check their presence to determine chip type, but if they were needed for the actual programming, there wouldn't be any way to program the SOT-6 version.)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HKJ on November 05, 2018, 09:08:25 am
I would look for the actual data protocol first, then the voltage levels and I doubt the chip will remember any state after a power cycle.

The first operation is probably reading some sort of chip identification.
Programming may be split into program memory and one or more configuration memories.
At least data memory needs an address and one or more data bytes for each programming pulse (Address may be auto increment).
Verification can be for each byte/block programmed or another run when finished.
Some programming algorithms consist of short pulses with a verification between each, when data match a couple more pulses are done to secure the data.


If this sort of protocol can be determined, it will probably be easier to see what voltage levels are used for each operation.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 05, 2018, 11:44:22 am
Maybe their strategy is to sell programmers :-\ :-\! :-\ Maybe they are copying the analog devices blackfin lines, selling the Dev tools and programmers so high that they would kill the product itself eventually, ask them so share the info! like rigol shard their way of hacking their scope to sell even more!!!! 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rjp on November 05, 2018, 12:38:25 pm

There is also a Flash/EEPROM re-programmable version of the chip, the PFS154C.
 

https://lcsc.com/product-detail/Others_PADAUK-Tech-PFS154-S16_C317613.html

thats a ripoff, 11c each in small quantities!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Whales on November 05, 2018, 03:01:34 pm
The padauk IDE, is AFAIK, the only way to create binaries for this platform.

Does this IDE let you access the output binaries yourself?  Or are they sent to the programmer directly without giving you access?  Comparing these binaries to the data waveforms would be useful.  You could observe if data is being shift-clocked in with the need for extra cycles (or similar).

If not, then finding out how the programming protocol works is only a tiny bit of the puzzle  :-/O 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: modrobert on November 05, 2018, 04:35:06 pm
Perhaps the programmer uses session encryption to the micro based on a unique serial number (read only) in the micro, to mitigate knockoffs (or "midnight batches" in approved factories) being produced.

Look for differences in initial handshake between different micros in the same batch.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 05, 2018, 04:43:28 pm
The padauk IDE, is AFAIK, the only way to create binaries for this platform.

Does this IDE let you access the output binaries yourself?  Or are they sent to the programmer directly without giving you access?  Comparing these binaries to the data waveforms would be useful.  You could observe if data is being shift-clocked in with the need for extra cycles (or similar).

If not, then finding out how the programming protocol works is only a tiny bit of the puzzle  :-/O

I guess you can use strings in the IDE, and they probably don't encrypt this, otherwise the microcontroller would be too complex. But even without strings, you can use inline assembler ("nop" etc.). Even if you don't know the encoding of the opcodes (but I guess you could look at the programming file), you could use 3 x command A, 4 x command B, and 5 x command C, and then search for a 3 x, 4 x, 5 x pattern. With this you could even reverse engineer the opcode encoding.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: glarsson on November 05, 2018, 05:55:19 pm
Perhaps the programmer uses session encryption to the micro based on a unique serial number (read only) in the micro, to mitigate knockoffs (or "midnight batches" in approved factories) being produced.
This is a 3¢ micro controller. To cheap to serialize during manufacturing.
Also, is there any economy in cloning a 3¢ part?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 05, 2018, 05:56:31 pm
Hi,

I had a quick look with IDA on the IDE generating the PDK output file after compilation.

The PDK file consists of a 256 byte header containing a 32 byte initialization "key" @0x000000E0

After the header is written the compiled binary is obfuscated (the algorithm used can not be called encryption ;-) using the initialization key from header @0x000000E0 and some magic values like "12345678h" and "55AA" and a lot of 16 bit XORs. It reads 32 byte chunks from the binary and obfuscates them in 4 loops, 2 bytes a at once in 4 statements.

It will not take me long to re-create the en/decrypt for this section, just some days I guess.

Small teaser:

I used the default program for 154C and inserted:

A = 'T';
A = 'E';
A = 'S';
A = 'T';

in the FPPA0 function right after the comment "// Insert Initial Code"

The IDE creates a memory segment of the unencrypted compiled binary @0x7EA90000
The binary section was 4kByte in total initialized with static values (seems they fill up the complete memory region the MCU can hold).

This is what I found somewhere in the memory section after compilation:

542F
452F
532F
542F

(54 = T, 45 = E, 53 = S )

-> first opcode we can learn from this is (seems to be a little endian design):

MOV A,<imm>   ->  <imm> 2F


In case somebody wants to play with IDA, the function to write "encrypted" files with header is located @0x0041B0DE


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 05, 2018, 09:14:35 pm
Some more opcodes... maybe somebody recognizes them (looks like 14 bits are used per opcode, but it not seems to be a PIC)

00 00 : NOP
67 00 : PCADD A
70 00 : WDRESET
72 00 : PUSHAF
73 00 : POPAF
75 00 : RESET
76 00 : STOPSYS
77 00 : STOPEXE
78 00 : ENGINT
79 00 : DISGINT
7A 00 : RET

9[ I ] 01 : MOV PA,A //IO
D[ I ]01 : MOV A,PA //IO

[PTR]1 03 : IDXM A,PTR
[PTR]0 03 : IDXM PTR,A

[M] 0B : MOV [MEM],A
[M] 0F : MOV A,[MEM]

[M] 13 : XCH M

IM 2F : MOV A,IMM

POS 30 : GOTO POS //POS is on WORDS
POS 38 : CALL POS   //POS is on WORDS

FF 3F : ? ? ? used as filler, maybe invalid opcode

----
I defined a function on top of "Project.C and you can just write assembler inside

void fun(void)
{
  MOV A,'T'
label1:
  MOV A,'E'
  GOTO label1
  //...

  //RET is inserted automatically from miniC
}

The function is placed in compiler output memory directly at start. Just 4 bytes in front of it which looks like this:
00 00  //NOP ?
09 30 //GOTO ...

They seem to come from "Project1.PRE" from the ".JMP FPPA0" directive

----

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FERCSA on November 05, 2018, 11:19:22 pm
Looks like it's a FPPA, Field Programmable Processor Array.

Here is some useful links:
http://fellong.blogspot.com/2007/07/fppa_14.html (http://fellong.blogspot.com/2007/07/fppa_14.html)
http://www.hy-star.com.tw/tech/MCU/mcu.html (http://www.hy-star.com.tw/tech/MCU/mcu.html)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 06, 2018, 04:26:03 am
The FFPA is their MCS11 chip, with 8 cores. Unfortunately I can't find it anywhere to buy. This would be a very interesting chip, similar to the Parallax Propeller, just a bit smaller, and presumably cheaper. The PMS150 has only one core.

But the more I think about it, I guess they developed it on their own and it is not a PIC clone or a clone of any other microcontroller. They couldn't have used the original die anyway, because PICs need 4 cycles and more per instruction, and the Padauk instruction set claims to need only one cycle for most instructions. And while very similar to the PIC instruction set, they have a few more instructions than PIC, especially their MCS11 flagship, like the wait instruction, which stops the CPU until an IO pin changes, which makes perfect sense for 8 cores, because it makes it easier to write fast bitbanging code for protocols like SPI in one dedicated core for the communication. But it is odd that they do such obfuscating, as if they want to hide something.

Maybe all their chips use the same die, and the other 7 cores are just disabled by software in the lower end chips? This would be a good reason for them not to publish the programming protocol :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: free_electron on November 06, 2018, 03:08:55 pm
This multilevel voltage programming is classic for PROM style devices.
This chip may very well be a true prom ( fuse or charge based ) and not a windowless eprom.

The reason for the multilevel voltages is to prevent accidental in-the-field corruption of the prom due to someone wiggling the pins in the wrong sequence.

They have analog comparators on the io pins used for programming ( simple window comparator made from 2 op-amps and a resistive divider. The op-amps aren't even real op-amps .. more like 4 transistors each, kind of how you make a schmitttrigger structure )

You can initialize and probably 'read' while within normal voltage on VCC. Meaning , below programming voltage. But you can't destroy anything.

Once programming voltage is applied other comparators come into play. These work between VCC and VPP (Programming voltage). One level is used for one function , another level for another function.

for example (hypothetical)
- send command to prepare for programming inside the VCC levels.
- turn on vpp
- set 6 volts on control pin : reset programming shifter
- set 7 volts : enable shifter
- now using the other pin : clock in data
- set 12 volts : burn
- set 9 volts : read back bits into shifter
- set 8 volts : turn shifter around ( the digital pin is now an output and you can read back the bits )

so these voltage all mean something : they control the on-chip programming logic.

This reminds me of the mechanism used to control trim bits in many devices. The advantage is that these voltages never will be applied int he fiedl and the entire 'programming' block is disabled.

the 'programmer' is nothing more than a simple shift register.
The fact that you pass from 5 volts VCC to 7 means you transitioned through 6 and thus caused a reset !!!

Then reverse engineering this be mindful of that.. if you see more than 1 level change : they have transitioned through a state !.

They could also use a multilevel self clocking mechanism.
 rise to 8 means  clock in a 0 . drop to 6 means clock in a 1. rising or dropping back to 7 means : advance counter a tick....

so the sequence
Code: [Select]

7878786768676867
 0 0 01 101 101
if the voltage transitions directly form 6 to 8 or 8 to 6 there is an implied '7' meaning : clock !  be weary of these things.
The on-board electronics is kept to a minimum in  area.... to make the chip cheap.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: glarsson on November 06, 2018, 03:16:47 pm
IF this device is a fusible link PROM device then it probably requires well controlled slopes on the programming pulse. Too fast rise time and the metal splashes over the silicon. Too slow damages the silicon due to localized heating or the bit will not program correctly.

Are fusible link PROMs manufactured today?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: TK on November 06, 2018, 03:31:03 pm
Padauk is not making any money selling the programmer, so why don't ask them for the programming protocol?  Adding support for  universal programmers like TL866 can help sell tons of 3cent microcontrollers.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: PA0PBZ on November 06, 2018, 03:31:27 pm
It looks to me that a lot could be learned from the original programmer, like how the pins are controlled?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ataradov on November 06, 2018, 04:25:55 pm
Padauk is not making any money selling the programmer, so why don't ask them for the programming protocol?
The have been asked and they refused to provide any information.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: SiliconWizard on November 06, 2018, 07:11:09 pm
It's unclear to me what incentive they would have to publicly release the programming protocol though. It usually ends up being more hassle than benefits for a tech company. And here I don't think that the kind of customers interested in devising their own tools are the ones who would buy their MCUs by the millions. So...

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ataradov on November 06, 2018, 07:19:09 pm
It usually ends up being more hassle than benefits for a tech company.
Tell that to Espressif. They were hiding stuff at first too, and then they quickly realized the power of the passionate community.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: drussell on November 06, 2018, 08:31:17 pm
Adding support for  universal programmers like TL866 can help sell tons of 3cent microcontrollers.

No, it won't.  People don't one-off program things like this except in development and prototyping.  These are the kind of chip that you order by the thousands, pre-programmed with whatever code you need for your application.  99.9999% of these chips sold need to be programmed at high speed, in bulk, not one-offs in some desktop programmer, that simply makes no sense.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: drussell on November 06, 2018, 08:34:42 pm
It's unclear to me what incentive they would have to publicly release the programming protocol though. It usually ends up being more hassle than benefits for a tech company. And here I don't think that the kind of customers interested in devising their own tools are the ones who would buy their MCUs by the millions. So...

Well, the people that buy them in the millions are going to get them mass-programmed, which the manufacturer or distributor will be set up with the equipment to do for you.  If you were using millions and wanted to program them in-house for some bizarre reason, they would still help you by either supplying the equipment or the engineering data to do that but that's very different than programming one-offs in a desktop programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 06, 2018, 11:16:08 pm
Hi,

For those curious people I wrote a little deobfuscator for PDK files (the compiled binary you get from IDE).

It's a command line utility called depdk which requires 2 parameters: inputfile and outputfile.

Example: ./depdk input.pdk output.bin

The header from the PDK file is thrown away and just the real (deobfuscated) binary data (which is written to the MCU) is written to the output file.

Compilation with gcc -o depdk depdk.c

Or use the attached compiled executable for Windows.

Have fun,

JS  8)

depdk.c

#include <stdio.h>
#include <stdint.h>
#include <string.h>

int main( int argc, const char * argv [] )
{
  if( 3 != argc ) {
    printf("usage: %s inputfile outputfile\n\n", argv[0]);
    return 0;
  }

  FILE* fin = fopen( argv[1], "rb");
  if( !fin ) { printf("Could not open %s for reading.\n", argv[1]); return -1; }

  FILE* fout = fopen( argv[2], "wb");
  if( !fin ) { printf("Could not open %s for writing.\n", argv[2]); return -1; }

  uint8_t hdrdata[0x100];
  if( sizeof(hdrdata) != fread( hdrdata, 1, sizeof(hdrdata), fin ) ) {
    printf("Error reading input file\n");
    return -1;
  }

  uint32_t version = *((uint32_t*)&hdrdata[0x08]);
  uint32_t datalen = *((uint32_t*)&hdrdata[0x20]);

  uint32_t extrahdr = *((uint16_t*)&hdrdata[0x26]) +
                      *((uint16_t*)&hdrdata[0x28]) +
                      *((uint16_t*)&hdrdata[0x2C]) +
                      *((uint16_t*)&hdrdata[0xD0]);
  if( version>=0x1c )
    extrahdr += *((uint8_t*)&hdrdata[0x49]);

  fseek( fin, extrahdr, SEEK_CUR );

  uint16_t key[0x10];
  memcpy( key, &hdrdata[0xE0], sizeof(key) );

  uint16_t kxorw7C92 = key[3]^key[14];
  uint16_t kxorw7E8A = key[7]^key[15];

  if( (version>=0x15) && (version<=0x17) ) {
    kxorw7C92 ^= 0x1234; kxorw7E8A ^= 0x5678;
  }

  uint16_t keyindex = 0;

  for( uint32_t fullpos=0; fullpos<datalen; fullpos+=32 ) {
    uint16_t data[0x20];
    if( sizeof(data) != fread( data, 1, sizeof(data), fin ) )
      break;

    uint32_t dataptr = 0;
    for( uint32_t j=0; j<4; j++ ) {
      uint16_t tmp_xor_key1;
      uint16_t tmp_xor_key2;

      keyindex += kxorw7C92;
      tmp_xor_key1 = data[dataptr];
      data[dataptr] += key[keyindex&0xF];
      dataptr++;
      key[fullpos&0xF] ^= tmp_xor_key1;

      keyindex += tmp_xor_key1;
      tmp_xor_key2 = data[dataptr];
      data[dataptr] = (data[dataptr] + kxorw7E8A ) ^ key[keyindex&0xF];
      dataptr++;
      key[kxorw7E8A&0xF] ^= kxorw7C92;

      keyindex ^= tmp_xor_key2;
      kxorw7C92 = data[dataptr];
      data[dataptr] += key[keyindex&0xF];
      dataptr++;
      key[kxorw7E8A&0xF] ^= 0x55AA;

      keyindex = (keyindex + kxorw7C92)>>1;
      kxorw7E8A = data[dataptr];
      data[dataptr] = (data[dataptr] - tmp_xor_key1) ^ key[keyindex&0xF];
      dataptr++;

      keyindex += kxorw7E8A;
      tmp_xor_key1 = data[dataptr];
      data[dataptr] ^= key[keyindex&0xF];
      dataptr++;
      key[kxorw7C92&0xF] += kxorw7E8A;

      keyindex ^= tmp_xor_key1;
      tmp_xor_key2 = data[dataptr];
      data[dataptr] = (data[dataptr] ^ kxorw7E8A) ^ key[keyindex&0xF];
      dataptr++;
      key[tmp_xor_key2&0xF] ^= tmp_xor_key1;

      keyindex ^= tmp_xor_key2;
      kxorw7C92 = data[dataptr];
      data[dataptr] += key[keyindex&0xF];
      dataptr++;
      key[tmp_xor_key1&0xF] += tmp_xor_key2;

      keyindex += kxorw7C92;
      kxorw7E8A = data[dataptr];
      data[dataptr] = (data[dataptr] + tmp_xor_key1) ^ key[keyindex&0xF];
      dataptr++;

      key[2] ^= tmp_xor_key1;
      key[4] += tmp_xor_key2;
      key[6] += kxorw7E8A;
      key[8] -= kxorw7C92;
      key[1] ^= key[15];
      key[3] ^= key[14];
      key[5] ^= key[13];
      keyindex += j;
    }

    if( sizeof(data) != fwrite( data, 1, sizeof(data), fout ) ) {
      printf("Error writing output file\n");
      return -1;
    }
  }

  fclose(fin);
  fclose(fout);

  return 0;
}

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 06, 2018, 11:53:47 pm
Just some useful info for understanding the MCU family and how to program it:

http://svn2.assembla.com/svn/mcu/ (http://svn2.assembla.com/svn/mcu/)

The examples using older processor types with 8 cores but most of it should be "understandbale"

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: SeoulBigChris on November 07, 2018, 02:27:30 am
It's unclear to me what incentive they would have to publicly release the programming protocol though. It usually ends up being more hassle than benefits for a tech company. And here I don't think that the kind of customers interested in devising their own tools are the ones who would buy their MCUs by the millions. So...

Disclaimer: I’ve never run a semiconductor company.

My reaction is the opposite, when I see policies like this. As far as I know, Paduk is in the business of selling semiconductors, not programmers. I contend that it’s more hassle to maintain a closed programming protocol. This forces you into the chip programmer business, taking your attention away from your core competency. Releasing the protocol so the various chip programmer companies and hobbyists can support your ICs should reduce their hassle, not increase it.

I have a similar take on providing a custom and apparently closed compiler. Do they have aspirations of becoming a compiler company as well?

I suppose it’s possible that the insides of their chips are so revolutionary and proprietary, that opening up these protocols would be akin to revealing their trade secrets. But I think that’s unlikely in this case.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ataradov on November 07, 2018, 02:31:45 am
With western companies there is a pretty benign explanation for why they don't release even the most trivial things - releasing something implies you will provide support. For whatever reason a concept of releasing things "as is" is not accepted.

But I doubt this is a problem for Padauk. Chinese companies have a habit of releasing a product and not providing any obvious support to the general public. And I like it - it lets us have products that we otherwise would not see, even if they are not well documented.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: SiliconWizard on November 07, 2018, 03:19:29 am
With western companies there is a pretty benign explanation for why they don't release even the most trivial things - releasing something implies you will provide support. For whatever reason a concept of releasing things "as is" is not accepted.

Yes, thus my "more hassle than benefits" point above.
Even if it's made clear you won't provide direct support, you're bound to one way or another. You will inevitably run into customers that will ask for tech support and make you waste significant time until they end up admitting they use unsupported tools.

But I doubt this is a problem for Padauk. Chinese companies have a habit of releasing a product and not providing any obvious support to the general public. And I like it - it lets us have products that we otherwise would not see, even if they are not well documented.

Possibly, but again why would they? That would still take some time to gather the bits and pieces in a consumable form for third parties, and possibly bother with uploading updates on a regular basis, etc. They may not even have a proper internal documentation themselves (that would be bad, but yes, that really happens!)

And I doubt they are interested in customers that will buy for a few bucks of their ICs.  ;D I also doubt that, maybe contrary to Espressif that have different products and targets, a large community of small companies or even amateur users would really help their business.
 :-//
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Bud on November 07, 2018, 06:02:35 am
The video was painful to watch. Too many cuts.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 11, 2018, 06:21:36 am
I contacted Padauk, will get a programmer and an ICE (unfortunately you need a different ICE than the one you can use for the PMS150C) for their new PMC884 chip with 8 cores and samples of the chip. Joe from Padauk sent me a datasheet for it. It is a bit strange why they don't publish it on their webpage: He says because it can be too difficult to program, maybe they don't want too many support requests. Anyway, he says the datasheet is not confidential and I'm allowed to show it to others for review:

http://www.frank-buss.de/tmp/pmc884.pdf (http://www.frank-buss.de/tmp/pmc884.pdf)

It is not really a multi-core chip, more like a mult-thread chip, because e.g. if you enable 2 cores and run it at 8 MHz, each core will run effectively at 4 MHz, round-robin. But still very useful for things like bitbanging on one core and application logic on another core, without the overhead of interrupts or complicated programming.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Hypernova on November 11, 2018, 02:47:50 pm
he says the datasheet is not confidential and I'm allowed to show it to others for review

Funny as the red watermark on every page reads "PADAUK confidential document"
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Sjaak on November 11, 2018, 04:52:55 pm
How about disassembling the programmer? Not expecting a regular mcu in there that can be read back but can give some clues howmany voltage levels there are, and even some silkscreen markings that provide info about signalnames.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 12, 2018, 05:40:10 am
Funny as the red watermark on every page reads "PADAUK confidential document"

Maybe it was confidential at some point, but it really doesn't make sense to hide it. This hardware thread concept looks very useful to simplify application development, without much drawbacks for power consumption or issues with real parallel cores, like synchronization and race conditions etc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Hypernova on November 12, 2018, 02:44:36 pm
Funny as the red watermark on every page reads "PADAUK confidential document"

Maybe it was confidential at some point, but it really doesn't make sense to hide it. This hardware thread concept looks very useful to simplify application development, without much drawbacks for power consumption or issues with real parallel cores, like synchronization and race conditions etc.

What they made is a Barrel Processor (https://en.wikipedia.org/wiki/Barrel_processor) which is a pretty old concept, so not sure what they have to hide. I have a real dislike for companies that take the confidential-by-default route.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 12, 2018, 08:15:50 pm
This is interesting, I didn't know the barrel processor concept.

The datasheet for the PMC884 says at one position it is patent pending, and at another position it is patented. I couldn't find an existing patent, only this:

https://patents.google.com/patent/US20050166170

Has the same name (FPPA), but looks like something completely different. But with the barrel processor I wonder if this counts as prior art and they can't patent it.

Meanwhile Joe told me the price for the PMC884: it is US$0.40 in larger quantities (but less than 100k). Don't know if this makes sense, because you could get 13 of the cheap 3 cent PMS150C for this price :) But might be still useful if you need it small in one IC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 14, 2018, 03:34:33 pm
I found some strings in "USB_Driver" folder inside of "Writer.PDK" (can be deobfuscated with small modified depdk).

Looks like the programmer uses 5V, 7.5V for VDD and 8V, 12V for VP (programing)

<<<  IC O.K. >>>
F/W Ver : 1.23 
DC Power Fail. 
DC Low Power.   
DC High Power. 
H/W VDD keep Hi.
H/W VD 5V fail.
H/W VDD 7V5 fail
H/W VDD 5V fail.
H/W VP 8V fail.
H/W VP 12V fail.


Maybe this helps interpreting the captured data.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: atc1441 on November 14, 2018, 06:36:19 pm
Hi, i think i found one Padauk chip in the wild.

It is in one of these STC Auto Programmer USB-TTL but i am not 100% shure eBay auction: #202070246074


As you see in the attachment the pinout is the same it is the tsop8 chip the other one is an CH340 Clone
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 16, 2018, 04:41:58 pm
Hi, I spent some time (actually a lot more than I wanted) to find out and write down all known instructions for the small type (1 core) processors (1 core processors start with a "1" like PMC154. PMC2... has 2 cores and PDK8... has 8 cores ).

The 1 core processors (the cheap ones ;-) ) do have a compact (14-bit) instruction set. The multi core processors seem to have a 16-bit instruction set.
Note: 14/16 bit instructions does not mean it is a 14/16 bit processor. They are all tiny 8 bit processors. Just the length of one instruction is 14/16 bit.

Here is a direct link:

https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html  :) :) :)


I also created a github project. Everybody is invited to contribute:

https://github.com/free-pdk

It just started with a single "documentation" repository. Next might be a disassembler and a simulator.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 16, 2018, 04:55:58 pm
That's really nice, you can add me if you like, my github name: FrankBuss
I could try to implement a FPGA emulation for it. This would allow realtime simulation in hardware (except for the ADCs) of the chip with all peripherals.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rhodges on November 16, 2018, 05:00:15 pm
Quote
Here is a direct link:
https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html  :) :) :)
Nice work! It looks like you might have all the important instructions decoded. Maybe it would be useful to have a program to parse the compiler output every time and alert if a "new" instruction comes out. After a while, we could be pretty confident about the instruction coding.

Thanks! I recently decided to move from PIC to STM8 for personal projects, but you are tempting me to rotate my brain 90 degrees to go back to PIC thinking...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: chicken on November 16, 2018, 05:10:34 pm
I'm tempted to add support for this architecture to radare2. https://github.com/radare/radare2
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 16, 2018, 05:27:17 pm
It looks like you might have all the important instructions decoded. Maybe it would be useful to have a program to parse the compiler output every time and alert if a "new" instruction comes out. After a while, we could be pretty confident about the instruction coding.

Actually I used the data sheets of all PMC/PMS1xx processors and typed in every possible instruction in the IDE and monitored the compiler output. So for sure the compiler will not generate more / unknown instructions from our code.

The holes are most likely unused spaces or instructions which they planned to implement but did not work out correctly. For instance AND IO,A / AND A,IO / OR IA,A / OR A,IO  are somehow missing and would fit perfectly in the "0x0100...0x017F" hole.

One way to try the "undocumented" instructions is to manually create the binary, inject these instructions and observe the result (like it was done decades ago for 6502).
Since OTP would be a bit painful for this I already ordered the FLASH based PFS154 (now waiting for it to arrive).

On the other hand, if the normal compiler does not create them, also a disassembler does not need to know them. Invalid instructions are a common thing which even exist on modern CPUs like ARM and Intel.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 16, 2018, 05:49:38 pm
Hi thank you for your work thus far.

@ js_12345678_55AA: Could you post the modifications you made to deobfuscate the PDKs in the USB_Driver directory?

Also: in the USB_Driver/USB directory there seems to be the firmware for the programmer (in obfuscated form):

P5SP_BOOT_UPDATER.fw
P5SP_G1.fw
P5SP_G2.fw
P5SP_TESTER.fw

from Dave's video the P5SP files could be for an STM32F072V8T6
and from the strings in the FPPA_IDE.EXE it seems to know how to upload them to the programmer
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 16, 2018, 08:22:00 pm
From the strings in FPPA_IDE.exe you can also gather voltage information from their test program of the programmer (P5SP_tester.fw):

0x63421c 70 69 Please remove all IC, and check VDD,\nVPP(PA5), PA0 / 3 / 4 / 7 is 0 V
0x634264 30 29 Please check VPP (PA5) = 4.6V
0x634284 31 30 Please check VPP (PA5) = 11.3V
0x6342a4 24 23 Please check VDD = 5.5V
0x6342bc 24 23 Please check VDD = 7.5V
0x6342d4 24 23 Please check VDD = 3.3V

and a list of instructions:

0x62dac0 16 15 MOV__A__IO_LIST
0x62dad0 16 15 MOV__IO_LIST__A
0x62dae0 16 15 XOR__A__IO_LIST
0x62daf0 16 15 XOR__IO_LIST__A
0x62db00 14 13 MOV__A__CONST
0x62db10 17 16 MOV__A__RAM_BYTE
0x62db24 17 16 MOV__RAM_BYTE__A
0x62db38 18 17 NMOV__A__RAM_BYTE
0x62db4c 18 17 NMOV__RAM_BYTE__A
0x62db60 18 17 IDXM__A__RAM_WORD
0x62db74 18 17 IDXM__RAM_WORD__A
0x62db88 17 16 LDTABL__RAM_WORD
0x62db9c 17 16 LDTABH__RAM_WORD
0x62dbb0 16 15 PUSHW__RAM_WORD
0x62dbc0 15 14 POPW__RAM_WORD
0x62dbd0 11 10 PUSHW__PCX
0x62dbdc 10 9 POPW__PCX
0x62dbe8 7 6 PUSHAF
0x62dbf0 6 5 POPAF
0x62dbf8 17 16 AND__A__RAM_BYTE
0x62dc0c 17 16 AND__RAM_BYTE__A
0x62dc20 14 13 AND__A__CONST
0x62dc30 16 15 OR__A__RAM_BYTE
0x62dc40 16 15 OR__RAM_BYTE__A
0x62dc50 13 12 OR__A__CONST
0x62dc60 17 16 XOR__A__RAM_BYTE
0x62dc74 17 16 XOR__RAM_BYTE__A
0x62dc88 14 13 XOR__A__CONST
0x62dc98 7 6 NOT__A
0x62dca0 14 13 NOT__RAM_BYTE
0x62dcb0 8 7 NEGC__A
0x62dcb8 7 6 NEG__A
0x62dcc0 15 14 NEGC__RAM_BYTE
0x62dcd0 14 13 NEG__RAM_BYTE
0x62dce0 16 15 CLEAR__RAM_BYTE
0x62dcf0 14 13 XCH__RAM_BYTE
0x62dd00 8 7 SWAP__A
0x62dd08 15 14 SWAP__RAM_BYTE
0x62dd18 6 5 SR__A
0x62dd20 13 12 SR__RAM_BYTE
0x62dd30 6 5 SL__A
0x62dd38 13 12 SL__RAM_BYTE
0x62dd48 7 6 SRC__A
0x62dd50 14 13 SRC__RAM_BYTE
0x62dd60 7 6 SLC__A
0x62dd68 14 13 SLC__RAM_BYTE
0x62dd78 18 17 NADD__A__RAM_BYTE
0x62dd8c 18 17 NADD__RAM_BYTE__A
0x62dda0 8 7 ADDC__A
0x62dda8 15 14 ADDC__RAM_BYTE
0x62ddb8 18 17 ADDC__A__RAM_BYTE
0x62ddcc 18 17 ADDC__RAM_BYTE__A
0x62dde0 8 7 SUBC__A
0x62dde8 15 14 SUBC__RAM_BYTE
0x62ddf8 18 17 SUBC__A__RAM_BYTE
0x62de0c 18 17 SUBC__RAM_BYTE__A
0x62de20 17 16 ADD__A__RAM_BYTE
0x62de34 17 16 ADD__RAM_BYTE__A
0x62de48 14 13 ADD__A__CONST
0x62de58 17 16 SUB__A__RAM_BYTE
0x62de6c 17 16 SUB__RAM_BYTE__A
0x62de80 14 13 SUB__A__CONST
0x62de90 14 13 INC__RAM_BYTE
0x62dea0 14 13 DEC__RAM_BYTE
0x62deb0 15 14 IZSN__RAM_BYTE
0x62dec0 8 7 IZSN__A
0x62dec8 15 14 DZSN__RAM_BYTE
0x62ded8 8 7 DZSN__A
0x62dee0 15 14 COMP__A__CONST
0x62def0 18 17 COMP__A__RAM_BYTE
0x62df04 18 17 COMP__RAM_BYTE__A
0x62df18 13 12 DELAY__CONST
0x62df28 16 15 DELAY__RAM_BYTE
0x62df38 9 8 DELAY__A
0x62df44 9 8 T0SN__CF
0x62df50 9 8 T1SN__CF
0x62df5c 9 8 T0SN__ZF
0x62df68 9 8 T1SN__ZF
0x62df74 9 8 SET0__CF
0x62df80 9 8 SET1__CF
0x62df8c 9 8 SET0__ZF
0x62df98 9 8 SET1__ZF
0x62dfa4 8 7 TOG__ZF
0x62dfac 8 7 TOG__CF
0x62dfb4 17 16 T0SN__IOBIT_LIST
0x62dfc8 17 16 T1SN__IOBIT_LIST
0x62dfdc 17 16 SET0__IOBIT_LIST
0x62dff0 17 16 SET1__IOBIT_LIST
0x62e004 16 15 TOG__IOBIT_LIST
0x62e014 18 17 SWAPC__IOBIT_LIST
0x62e028 18 17 WAIT0__IOBIT_LIST
0x62e03c 18 17 WAIT1__IOBIT_LIST
0x62e050 14 13 T0SN__RAM_BIT
0x62e060 14 13 T1SN__RAM_BIT
0x62e070 14 13 SET0__RAM_BIT
0x62e080 14 13 SET1__RAM_BIT
0x62e090 19 18 CEQSN__A__RAM_BYTE
0x62e0a4 16 15 CEQSN__A__CONST
0x62e0b4 20 19 CNEQSN__A__RAM_BYTE
0x62e0c8 17 16 CNEQSN__A__CONST
0x62e0dc 14 13 GOTO__ADR_ABS
0x62e0ec 14 13 GOTO__ADR_OFS
0x62e0fc 16 15 IGOTO__RAM_WORD
0x62e10c 14 13 CALL__ADR_ABS
0x62e11c 14 13 CALL__ADR_OFS
0x62e12c 16 15 ICALL__RAM_WORD
0x62e13c 15 14 LGOTO__ADR_ABS
0x62e14c 15 14 LCALL__ADR_ABS
0x62e160 5 4 RETI
0x62e168 11 10 RET__CONST
0x62e174 14 13 PMODE__P_MODE
0x62e184 8 7 STOPSYS
0x62e18c 8 7 STOPEXE
0x62e194 16 15 LDT16__RAM_WORD
0x62e1a4 16 15 STT16__RAM_WORD
0x62e1b4 7 6 ENGINT
0x62e1bc 8 7 DISGINT
0x62e1c4 8 7 WDRESET
0x62e1cc 6 5 RESET
0x62e1dc 9 8 PCADD__A

There are also quite a few compiler directives, but they are all over the place
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 16, 2018, 09:20:47 pm
The instruction list above seems to be a generic one, describing all theoretically available instructions.
The actually available instructions for a specific chip are given by the specific inc file in the INC_PDK directory and the symbol file (defined in the inc file and located in the Symbol directory)
(There is a lot of additional data in that file, maybe they also define what address modes can be used and which instruction can also use flags or io's as operands etc.)

example:
PMS150C (44 Instructions)
INSTRUCTION
CALL
GOTO
ADD
SUB
CEQSN
AND
OR
XOR
MOV
T0SN
T1SN
SET0
SET1
ADDC
SUBC
IZSN
DZSN
INC
DEC
CLEAR
XCH
NOT
NEG
SRC
SLC
RET
IDXM
STT16
LDT16
WDRESET
PUSHAF
POPAF
RESET
STOPSYS
STOPEXE
ENGINT
DISGINT
RETI
PCADD
SWAP
TRAP
NOP
LDSPTL
LDSPTH

PFS154 (52 Instructions)
INSTRUCTION
CALL
GOTO
ADD
SUB
CEQSN
CNEQSN
AND
OR
XOR
MOV
T0SN
T1SN
SET0
SET1
ADDC
SUBC
IZSN
DZSN
INC
DEC
CLEAR
XCH
NOT
NEG
SRC
SLC
NADD
COMP
SWAP
STT16
LDT16
IDXM
RET
LDTABL
LDTABH
WDRESET
PUSHAF
POPAF
RESET
STOPSYS
STOPEXE
ENGINT
DISGINT
RETI
MUL
NEGC
PCADD
SWAP
TRAP
NOP
LDSPTL
LDSPTH
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 16, 2018, 11:01:10 pm
Found 2 more instructions which are not in manual:

LDSPTL   0x0006
LDSPTH  0x0007

They are fixed instructions with no arguments.

Speculation...
Looks like it is a syntax which uses L and H 
Since the stack pointer is mapped on IO 0x02 and does not have High or Low, the "SP" inside the name might me misleading

----
There are 2 more undocumented instructions which the IDE knows but refuses to compile. I tried many many different 1xx processors:

WORD data
...

LDTABL  data
LDTABH  data

Compiler always says: "The 'LDTABx' not be supported at PFS154" (for every 1xx processor I tried)

All other instructions from the list are already mapped.

One special exception is the "TRAP" instruction. The IDE just put's a "NOP" inside the binary. I assume this is used for the ICE only... so need to wait for my ICE to arrive ;D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 16, 2018, 11:12:27 pm
@ js_12345678_55AA: Could you post the modifications you made to deobfuscate the PDKs in the USB_Driver directory?

I updated the initial post (both source and windows binary)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 08:58:02 am
Speaking of ICE
The USB_Driver/USB directory also seems to contain the firmware for the ICE (*.usb and *.hid files)
As far as I can tell this should be firmware for an Cypress EZ-USB FX2LP Chip CY7C68013A (8051 code) it is not obfuscated.

I assume that the ICE*PDK files are for GAL/PAL/FPGA device seen in the video of the ICE. (Cypress even markets the chip as an FPGA companion "Booting an FPGA from FX2LP" so probably an FPGA.

AN63620 - Configuring a Xilinx Spartan-3E FPGA Over USB Using EZ-USB FX2LP™:
"This  application  note  demonstrates  a  technique  for  dynamically  configuring  a  Xilinx  Spartan-3E  Field  Programmable  Gate Array  (FPGA)  over  USB  using  EZ-USB  FX2LP,  a  high-speed  USB  peripheral  controller.  After  the  FPGA  is  configured, FX2LP  can  act  as  a  high-speed  data  path  between  the  USB  host  and  the  FPGA.  This  capability of  FX2LP  enhances 
FPGA-based USB applications such as logical analyzers, oscilloscopes, image processing,
and high-speed data acquisition."

They are all wildly different from each other, which would make sense if they all are for differnt cores.
The file sizes are however all divisible by 64 -> Logic cells/blocks?




ICE_3.usb and WRITER_5.usb on the other hand are almost identical, so I assume thats for the same thing (as far as I understand thats the multicore ICE)

ICE5.fw would then be the obfuscated single core firmware for the ICE that Dave has. It seems that they still use a Cypress FX2 chip, so probably almost identical to ICE_3.usb.
Maybe that helps with deobfuscation.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 17, 2018, 10:55:58 am

@ js_12345678_55AA:

Also: in the USB_Driver/USB directory there seems to be the firmware for the programmer (in obfuscated form):

P5SP_BOOT_UPDATER.fw
P5SP_G1.fw
P5SP_G2.fw
P5SP_TESTER.fw

from Dave's video the P5SP files could be for an STM32F072V8T6

You asked for it... here it is:

It's a command line utility called defw which requires 2 parameters: inputfile and outputfile.

Example: ./defw input.fw output.bin

Compilation with gcc -o defw defw.c

Or use the attached compiled executable for Windows.

Have fun,

JS  8)

P.S. works for all *.fw files and also the *.hid files in "USB_Driver/USB" directory. All other files (*.usb) there seem not to be obfuscated. For the PDK files use "depdk".

defw.c


#include <stdio.h>
#include <stdint.h>
#include <string.h>

int main( int argc, const char * argv [] )
{
  if( 3 != argc ) {
    printf("usage: %s inputfile outputfile\n\n", argv[0]);
    return 0;
  }

  FILE* fin = fopen( argv[1], "rb");
  if( !fin ) { printf("Could not open %s for reading.\n", argv[1]); return -1; }

  FILE* fout = fopen( argv[2], "wb");
  if( !fin ) { printf("Could not open %s for writing.\n", argv[2]); return -1; }
 
  uint16_t data[0x10000];
  int lenwords = fread( data, sizeof(uint16_t), sizeof(data)/sizeof(uint16_t), fin );
  if( lenwords<=0 ) {
     printf("Could not read %s.\n", argv[1]); return -1;
  }

  for( uint32_t i=0; i<lenwords; i++ ) {
    data[ i ] ^= i;
    if( i & 1 ) data[ i ] ^= 0x55;
    else
    if( i & 2 ) data[ i ] ^= 0xAA23;
    else
    if( i & 4 ) data[ i ] ^= 0x3759;
    else
      data[ i ] ^= 0xAFCD;
    data[ i ] ^= (lenwords-i-1)<<3;
  }
   
  if( lenwords != fwrite( data, sizeof(uint16_t), lenwords, fout ) ) {
    printf("Error writing output file\n");
    return -1;
  }

  fclose(fin);
  fclose(fout);

  return 0;
}



... it is indeed STM32 firmware in there :-)


Edit: fixed forum formatting of data[ i ]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 17, 2018, 11:07:18 am
Hi,

seems youtuber "bigclivedotcom" spotted a PADAUK MCU containing device in the wild:

https://www.youtube.com/watch?v=gJKy20wfIvg (https://www.youtube.com/watch?v=gJKy20wfIvg)

 :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 11:24:16 am
Hey thanks!

Whats interesting is that there is a "simple emulator" that isnt available anywhere:
5S-I-S0 2B

http://www.padauk.com.tw//upload/ICEmanual/5S-ICE_UM_EN_V002_20181105.pdf (http://www.padauk.com.tw//upload/ICEmanual/5S-ICE_UM_EN_V002_20181105.pdf) (page 15)

But: there is an dev board with Cypress FX2 Chip
https://de.aliexpress.com/wholesale?catId=0&SearchText=EZ-USB+FX2LP+CY7C68013A (https://de.aliexpress.com/wholesale?catId=0&SearchText=EZ-USB+FX2LP+CY7C68013A)
for ~3.5 USD

If we can find out what FPGA they use  :popcorn:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 11:29:38 am
small error:
data ^= ...
should read
 data square brackets i ^= ... (Forum doesnt let me post square brackets  :-//)
fixed locally and seems to work
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 11:40:55 am
and more voltages appear:
T:CN5/CN6
VPP_PWR != 11V
T:CN7
T:CN12/CN6/CN5
VPP_PWR != 0V
VDD_PWR != 7.8V
T:CN11
T:CN11/CN4/CN3
VDD_PWR != 0V
HVPP_IC != 11V
T:IC_PA5
T:Q32
VPP_IC != 0V
VDD_IC != 7.8V
T:IC_VDD
T:Q9
VDD_IC != 0V
`pGp
d!/H
VDD_PWR != 3V
 T:CN11
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 12:28:03 pm

seems youtuber "bigclivedotcom" spotted a PADAUK MCU containing device in the wild:


Too bad he doesnt desolder the chip to show the bottom so we can see the package markings.

Just FYI package markings on the chips I have:
PMS150C: YS17 RBAAADO 1839XA0
PMC232-S16A: FS20 FC62450 1737YAD
PFS154-S16: YP56 R2E9691 1609XBD
Bj8P509FNB (supposedly clone of elan 13-bit clone of microchip 12c509): BJY180338
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 17, 2018, 02:34:14 pm
I was thinking about creating a library (may be called "libpdk") which contains all the code one may need to create tools for these MCUs. The lib would contain stuff like the PDK decryption/encryption code, the instruction list with their opcode encoding/decoding rules, etc... then all the tools like disassembler, assembler, emulator, etc... can link to the same library. This would let us have only one codebase where the "important stuff" is so if we need to make changes and adjustments (like adding new instrs etc) we wouldn't have to change every single other tool. I'm starting to layout the instruction list in C++ in a way that can be used both to assemble, disassemble or emulate stuff. Is there a place for people interested in helping with the code to chat with the others so we somehow coordinate the work? Like a Slack or Discord channel or something
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 03:00:49 pm
IMHO it would be more useful to add the padauk controllers to already existing toolchains like radare
similarly to 8051 or 6502 or pic that are already there:

https://github.com/radare/radare2/tree/master/libr/asm/arch/8051 (https://github.com/radare/radare2/tree/master/libr/asm/arch/8051)
https://github.com/radare/radare2/tree/master/libr/asm/arch/6502 (https://github.com/radare/radare2/tree/master/libr/asm/arch/6502)
https://github.com/radare/radare2/tree/master/libr/asm/arch/avr (https://github.com/radare/radare2/tree/master/libr/asm/arch/avr)
https://github.com/radare/radare2/tree/master/libr/asm/arch/pic (https://github.com/radare/radare2/tree/master/libr/asm/arch/pic)

You can also add file formats like this:
https://github.com/radare/radare2/blob/master/libr/io/p/io_ihex.c (https://github.com/radare/radare2/blob/master/libr/io/p/io_ihex.c)

I think it would save you and others a lot of work, because most of the underlying work has already been done and tested.
Also radare has already got quite a few tools build in for analysis, disassembling and low level debugging as you can see here:

https://www.megabeets.net/reverse-engineering-a-gameboy-rom-with-radare2/ (https://www.megabeets.net/reverse-engineering-a-gameboy-rom-with-radare2/)

For compiling it might be interesting to add this architecture to sdcc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 17, 2018, 04:16:35 pm
Too bad he doesnt desolder the chip to show the bottom so we can see the package markings.

You asked for it...  :)

Just stopped at ALDI and saw them having a similar LED Christmas lights offering for 2.99 EUR.

I bought and opened it (without powering it on, because "Don't turn it on, take it apart!" 8) ) ...

... and yes, PCB and MCU looks same as from bigclivedotcom's video.

But to my surprise it is having a 32kHz crystal so it can do much better than the more cost optimized version bigclivedotcom was testing.

Last picture shows the MCU from back side. I'm pretty sure it is a PMC154 (just the cheapest and the pinout for GND, VDD, crystal also matches).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: GeorgeOfTheJungle on November 17, 2018, 04:17:17 pm
(Forum doesnt let me post square brackets  :-//)

Look here: https://wiki.simplemachines.org/smf/Alphabetical_list_of_all_bulletin_board_codes

The ones that might work for that are pre or nobbc, me thinks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 04:35:59 pm

Last picture shows the MCU from back side. I'm pretty sure it is a PMC154 (just the cheapest and the pinout for GND, VDD, crystal also matches).


I dont think so. The chips I have have 3 lines of markings. This just has the one.
No Bojuxing Industry BJ8P509FNB either because thats more laser carved and the chip marking you have seems inkjetted.

All these chips are probably very interchangable anyhow. Or they just rewrite the code, after all these are throw away products

Maybe ALDI has the premium version for germans  :-DD thus the crystal for milisecond switching precision
(seriously the cheapest crystal I could find on lcsc costs more than the pms150c  :scared: utter madness)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 17, 2018, 10:17:42 pm
This isnt complete but its a start.
If you would like to extend this, youre welcome
Its based on
https://github.com/limkokhole/radare2/wiki/Implementing-a-new-architecture
and by no means any good, but I think its not too hard to get it usable.

create a directory. put the two files in it. install radare2 if you havent already.
make
sudo make install

I also had to
cp /usr/lib/radare2/last/* ~/.config/radare2/plugins
otherwise the plugin isnt recognized

rasm2 -L should list it at the end
and then you can
rasm2 -a PADAUK -d 0x0069
to get:  neg a

padauk.c

Code: [Select]
/* Padauk disassembler plugin for radare */

#include <r_asm.h>
#include <r_lib.h>
#include <string.h>

static struct {
ut8 op1;
ut8 op2;
char *name;
} ops[] = {
{0x00, 0x00, "nopi"},
{0x00, 0x60, "addc a"},
{0x00, 0x61, "subc a"},
{0x00, 0x62, "izsn a"},
{0x00, 0x63, "dzsn a"},
{0x00, 0x64, "?"},
{0x00, 0x65, "?"},
{0x00, 0x66, "?"},
{0x00, 0x67, "pcadd a"},
{0x00, 0x68, "not a"},
{0x00, 0x69, "neg a"},
{0x00, 0x6a, "sr a"},
{0x00, 0x6b, "sl a"},
{0x00, 0x6c, "src a"},
{0x00, 0x6d, "slc a"},
{0x00, 0x6e, "swap a"},
{0x00, 0x6f, "?"},
{0x3f, 0xff, NULL}};

static int _PADAUKDisass (RAsm *a, RAsmOp *op, const ut8 *buf, int len) {
int i;
op->size = 2;
for (i=0; ops[i].name != NULL; i++) {
if (ops[i].op1 == buf[0]) {
if (ops[i].op2 == buf[1]) {
sprintf (op->buf_asm, "%s", ops[i].name);
break;
}
}
}
return op->size;
}

RAsmPlugin r_asm_plugin_padauk = {
        .name = "PADAUK",
        .arch = "PADAUK",
        .license = "LGPL3",
        .bits = 16,
        .desc = "Padauk disassembler",
        .disassemble = &_PADAUKDisass,
};

#ifndef CORELIB
struct r_lib_struct_t radare_plugin = {
        .type = R_LIB_TYPE_ASM,
        .data = &r_asm_plugin_padauk
};
#endif

Makefile

Code: [Select]
NAME=padauk
R2_PLUGIN_PATH=$(shell r2 -hh|grep LIBR_PLUGINS|awk '{print $$2}')
CFLAGS=-g -fPIC $(shell pkg-config --cflags r_asm)
LDFLAGS=-shared $(shell pkg-config --libs r_asm)
OBJS=$(NAME).o
SO_EXT=$(shell uname|grep -q Darwin && echo dylib || echo so)
LIB=$(NAME).$(SO_EXT)

all: $(LIB)

clean:
rm -f $(LIB) $(OBJS)

$(LIB): $(OBJS)
$(CC) $(CFLAGS) $(LDFLAGS) $(OBJS) -o $(LIB)

install:
cp -f $(NAME).$(SO_EXT) $(R2_PLUGIN_PATH)

uninstall:
rm -f $(R2_PLUGIN_PATH)/$(NAME).$(SO_EXT)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 18, 2018, 12:27:02 pm
This is a slightly improved version tested with radare 3.1 git.
The documentation for radare is shall we say "sparse" and every backend seems to have multiple layers of indirection and slightly different ways of going about it, especially for the assembler.
But once you found a way it works quite nicely. This is also not very complete and thus minimalistic because I dont know what the best way to de/encode the instructions is.
The table approach has the advantage of being inversible i.e the dissassembler is the inverse of the assembler, but its quite pointless to do it in this manor for instructions that take addresses etc.

Use the makefile from above.
make && sudo make install
and then you can do
rasm2 -a padauk -d 0x0073
to get "popaf" or
rasm2 -a padauk 'addc a'
to get "0x0060"
and you also get stuff like this
rasm2 -a padauk 'nop; ret; reti; addc a; sr a;'
rasm2 -a padauk -d 0x0000006000720073
for free

padauk.c
Code: [Select]
/* Padauk (dis)assembler plugin for radare 3.1 git - DocBen 2018 */

#include <r_asm.h>
#include <r_lib.h>
#include <string.h>

static struct {
ut16 op;
char *name;
} ops[] = {
{0x0000, "nop"},
{0x0060, "addc a"},
{0x0061, "subc a"},
{0x0062, "izsn a"},
{0x0063, "dzsn a"},
{0x0064, "?"},
{0x0065, "?"},
{0x0066, "?"},
{0x0067, "pcadd a"},
{0x0068, "not a"},
{0x0069, "neg a"},
{0x006c, "src a"},
{0x006d, "slc a"},
{0x006a, "sr a"},
{0x006b, "sl a"},
{0x006e, "swap a"},
{0x006f, "?"},
{0x0070, "wdreset"},
{0x0071, "?"},
{0x0072, "pushaf"},
{0x0073, "popaf"},
{0x0074, "?"},
{0x0075, "reset"},
{0x0076, "stopsys"},
{0x0077, "stopexe"},
{0x0078, "engint"},
{0x0079, "disgint"},
{0x007b, "reti"},
{0x007a, "ret"},
{0x007c, "mul"},
{0x007d, "?"},
{0x007e, "?"},
{0x007f, "?"},
{0x4000, NULL}};

int _PADAUKDisass (RAsm *a, RAsmOp *op, const ut8 *buf, int len) {
int i;
op->size = 2;
const char *buf_asm = "unknown";
for (i=0; ops[i].name != NULL; i++) {
if (ops[i].op == 0x100 * buf[0] + buf[1]) {
buf_asm = sdb_fmt ("%s", ops[i].name);
break;
}
}
r_strbuf_set (&op->buf_asm, buf_asm);
return op->size;
}

int _PADAUKAss (RAsm *a, RAsmOp *op, const char *buf) {
int i;
op->size = 2;
ut16 opbuf = 0x4000;
const char *buf_hex = "unknown";
for (i = 0; ops[i].name != NULL; i++) {
if (!strncmp(ops[i].name, buf, strlen(ops[i].name))) {
opbuf = ops[i].op;
buf_hex = sdb_fmt ("0x%.4X\n", opbuf);
break;
}
}
r_strbuf_set (&op->buf_hex, buf_hex);
return op->size;
}

RAsmPlugin r_asm_plugin_padauk = {
        .name = "padauk",
        .arch = "padauk",
        .license = "LGPL3",
        .bits = 16,
        .desc = "Padauk (dis)assembler",
        .disassemble = &_PADAUKDisass,
        .assemble = &_PADAUKAss,
};

#ifndef CORELIB
struct r_lib_struct_t radare_plugin = {
        .type = R_LIB_TYPE_ASM,
        .data = &r_asm_plugin_padauk
};
#endif
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 18, 2018, 08:15:18 pm
Playing further with radare I noticed that there are mostly disassembler backends but only a few assemblers.
I kind of like the idea of having something table driven that allows for a certain symmetry of assembler and disassembler.
Also looks more like a datasheet. Again not complete but recognizes the instructions given, if you want more instructions its literally copy and paste from the website somewhere above.

Don't know if I'll be able to finish this soon though. Just to give an idea that this could be generalized I did the same for pic12 and at least it looks good ;)

Code: [Select]
/* Padauk (dis)assembler plugin for radare 3.1 git - DocBen 2018
now looking more like a datasheet
*/

#include <r_asm.h>
#include <r_lib.h>
#include <string.h>

static struct {
char *op;
char *name;
ut8 args;
char *comment;
} ops[] = {
// memory mapped io i (6-bit)
// nth bit n (3-bit)
// memory address m (6 bit)
// memory address M (7 bit)
// immediate c (8 bit)
// address k (11 bit)
//"binary representation","mnemonic"(,"num parameters (could be inferred)"),"comment"
"0000.0000.0000.0000", "nop", 0, "does nothing (tm)",
"0000.0000.0110.0000", "addc a", 1, "A ← A + CF",
"0000.0000.11ii.iiii", "xor io,a", 2, "IO ← IO ^ A",
"0000.0001.10ii.iiii", "mov io,a", 2, "IO ← A",
"0000.0001.11ii.iiii", "mov a,io", 2, "A ← IO",
"0000.0010.cccc.cccc", "ret c", 1, "",
"0000.0011.1MMM.MMM0", "idxm M, a", 2, "[M] ← A (last bit of M set to 0, M must be word aligned, 2 cycles)",
"0000.0011.1MMM.MMM1", "idxm a, M", 2, "a ← [M] (last bit of M set to 1, M must be word aligned, 2 cycles)",
"0000.010n.nnii.iiii", "swapc io.n", 2, "",
"0000.0110.0MMM.MMMM", "comp a, M", 2, "",
"0010.000n.nnmm.mmmm", "t0sn m.n", 2, "",
"0011.0kkk.kkkk.kkkk", "goto k", 1, "goto address",
"0011.1kkk.kkkk.kkkk", "call k", 1, "call address",
"2222.2222.2222.2222", NULL, 0, "",
};


void bitstring(uint16_t val, char buffer[]) {
int size = 20;
buffer[--size] = 0;
while (size > 0) {
buffer[--size] = (val % 2 ? '1' : '0');
if ( size % 5 == 0 && size > 0) buffer[--size] = '.';
val = val >> 1;
}
}

int _PADAUKDisass (RAsm *a, RAsmOp *op, const ut8 *buf, int len) {
int i;
op->size = 2;
const char *buf_asm = "unknown";
char buf_bin[40];
bitstring(0x100 * buf[0] + buf[1], buf_bin);
for (i=0; ops[i].name != NULL ; i++) {
for (int j = 0; j < 20; j++) {
if (ops[i].op[j] != buf_bin[j]) {
if (ops[i].op[j] != '0' && ops[i].op[j] != '1') { // treat all letters as dont care
continue;
} else {
break;
}
}
if (j == 19) {
buf_asm = sdb_fmt ("%s = %s ; %s", buf_bin, ops[i].name, ops[i].comment);
r_strbuf_set (&op->buf_asm, buf_asm);
return op->size;
}
}
}
r_strbuf_set (&op->buf_asm, buf_asm);
return op->size;
}

int _PADAUKAss (RAsm *a, RAsmOp *op, const char *buf) {
int i;
op->size = 2;
ut16 opbuf = 0x4000;
const char *buf_hex = "unknown";
for (i = 0; ops[i].name != NULL; i++) {
if (!strncmp(ops[i].name, buf, strlen(ops[i].name))) {
//opbuf = ops[i].op;
buf_hex = sdb_fmt ("0x%.4X\n", opbuf);
break;
}
}
r_strbuf_set (&op->buf_hex, buf_hex);
return op->size;
}

RAsmPlugin r_asm_plugin_padauk = {
        .name = "padauk2",
        .arch = "padauk2",
        .license = "LGPL3",
        .bits = 16,
        .desc = "Padauk (dis)assembler",
        .disassemble = &_PADAUKDisass,
        .assemble = &_PADAUKAss,
};

#ifndef CORELIB
struct r_lib_struct_t radare_plugin = {
        .type = R_LIB_TYPE_ASM,
        .data = &r_asm_plugin_padauk
};
#endif

PIC12
Code: [Select]
static struct {
char *op;
char *name;
ut8 args;
char *comment;
} ops[] = {
// direction d (1 bit)
// tri-state register t (2 bit)
// nth bit b (3-bit)
// register bank (3 bit)
// register f (5 bit)
// immediate c (8 bit)
// address k (8 bit)
// address K (9 bit)
//"binary representation","mnemonic"(,"num parameters"), "comment"
"0000.0000.0000.0000", "nop", 0, "No operation (MOVW 0,W)",
"0000.0000.0000.0010", "option", 0, "Copy W to OPTION register",
"0000.0000.0000.0011", "sleep", 0, "Go into standby mode",
"0000.0000.0000.0100", "clrwdt", 0, "Restart watchdog timer",
"0000.0000.0000.01tt", "tris t", 0, "Copy W to tri-state register (f = 1, 2 or 3)",
"0000.0000.0001.0BBB", "movlb k", 1, "Set bank select register to k",
"0000.0000.0001.1110", "return", 0, "Return from subroutine, W unmodified",
"0000.0000.0001.1111", "retfie", 0, "Return from interrupt; return & enable interrupts",
"0000.0000.001f.ffff", "movwf f", 1, "dest ← W",
"0000.0000.01df.ffff", "clr f,d", 2, "dest ← 0, usually written CLRW or CLRF f",
"0000.0000.10df.ffff", "subwf f,d", 2, "dest ← f−W (dest ← f+~W+1)",
"0000.0000.11df.ffff", "decf f,d", 2, "dest ← f−1",
"0000.0001.00df.ffff", "iorwf f,d", 2, "dest ← f | W, logical inclusive or",
"0000.0001.01df.ffff", "andwf f,d", 2, "dest ← f & W, logical and",
"0000.0001.10df.ffff", "xorwf f,d", 2, "dest ← f ^ W, logical exclusive or",
"0000.0001.11df.ffff", "addwf f,d", 2, "dest ← f+W",
"0000.0010.00df.ffff", "movwf f,d", 2, "dest ← f",
"0000.0010.01df.ffff", "comf f,d", 2, "dest ← ~f, bitwise complement",
"0000.0010.10df.ffff", "incf f,d", 2, "dest ← f+1",
"0000.0010.11df.ffff", "decfsz f,d", 2, "dest ← f−1, then skip if zero",
"0000.0011.00df.ffff", "rrf f,d", 2, "dest ← CARRY<<7 | f>>1, rotate right through carry",
"0000.0011.01df.ffff", "rlf f,d", 2, "dest ← F<<1 | CARRY, rotate left through carry",
"0000.0011.10df.ffff", "swapf f,d", 2, "dest ← f<<4 | f>>4, swap nibbles",
"0000.0011.11df.ffff", "incfsz f,d", 2, "dest ← f+1, then skip if zero",
"0000.0100.bbbf.ffff", "bcf f,b", 2, "Clear bit b of f",
"0000.0101.bbbf.ffff", "bsf f,b", 2, "Set bit b of f",
"0000.0110.bbbf.ffff", "btfsc f,b", 2, "Skip if bit b of f is clear",
"0000.0111.bbbf.ffff", "btfss f,b", 2, "Skip if bit b of f is set",
"0000.1000.cccc.cccc", "retlw c", 2, "Set W ← k, then return from subroutine",
"0000.1001.kkkk.kkkk", "call k", 2, "Call subroutine, 8-bit address k",
"0000.101K.KKKK.KKKK", "goto k", 2, "Jump to 9-bit address k",
"0000.1100.cccc.cccc", "movlw c", 2, "W ← c",
"0000.1101.cccc.cccc", "iorlw c", 2, "W ← c | W, bitwise logical or",
"0000.1110.cccc.cccc", "andlw c", 2, "W ← c & W, bitwise and",
"0000.1111.cccc.cccc", "xorlw c", 2, "W ← c ^ W, bitwise exclusive or",
"2222.2222.2222.2222", NULL, 0, "",
};
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 10:11:11 am
Nice job, would it be possible to make a github repo out of it?

Anyhow my idea for a "universal" instruction table was to have a list of objects like this, if this can somehow interest you:

opcode (16bit)
opcode_mask (16bit)
parameters (array)
[
  {
    type {IO/MEM/IMM/...}
    length (in bits)
    pos (bit n#)
  }
]

There are not a lot of instructions that have more than one parameter encoded, but there are still some, so having an array of parameters descriptions covers everything. Let's call the object above "instr_t". You could write functions to create an instr_t from an assembly line, from an opcode or whatever. Also you could write functions to convert it to an opcode, to an assembly line or to emulate the thing (or maybe the emulator is just a big switch on the opcode and you do everything manually, idk). The point is, this should cover everything and be pretty flexible and somewhat clean.

It may be faster than your current approach (which I like anyway, it is very readable IMHO) but by pattern matching like that may not be the most efficient thing, also you'll have to reconstruct the parameter values and other stuff which would be easier with a table like mine, at least that's what I anticipate.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 10:20:31 am
Also you may want the make install rule to install the plugin under the user plugins directory (on my Linux system it's ~/.local/share/radare2/plugins) which is a bit less invasive ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 01:58:23 pm
The architecture's engagingly minimal --- memory/memory architecture, one register! I actually have a self-hosting tiny compiler (<plug> http://cowlark.com/cowgol (http://cowlark.com/cowgol) </plug>) which would map very nicely onto this thing. Sadly, it doesn't have enough RAM to run the compiler on itself...

If anyone comes up with a simulator which will run PDK files, I'd love to know about it!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 02:37:44 pm
Uhm, I just noticed the PMS150/PMS150C opcodes are different from the PMS154C ones, while still being 14-bit wide. Seems like there are multiple encodings for the same instructions.

For instance:

mov A, 0xAA       -> 0x17AA
mov <addr>, A    -> 0x05C.. something like that
pcadd a               -> 0x0017
wdreset                -> 0x0030

But they're not totally different, most of the time it's just one bit off. Also the PDK fill pattern is 0x1FFF instead of 0x3FFF.

This may need some investigation.

edit: actually no value goes beyond 0x1FFF, I should have noticed that before. Seems like they shaved one bit off and the opcodes are 13-bit (?) if that makes any sense.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 19, 2018, 03:11:50 pm
If anyone comes up with a simulator which will run PDK files, I'd love to know about it!

Maybe it could be added as a target for QEMU. It has already all kinds of infrastructure functions to implement a new target without too much effort, and it is very fast, because it translates the code to native assembler code on the fly, like a JIT compiler. And it has already functions for timers, interrupts etc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 03:27:18 pm
If anyone comes up with a simulator which will run PDK files, I'd love to know about it!

I intend to get support for some Padauk devices into SDCC. For this, they'd need to be supported in the asxxxx fork that SDCC uses, the linker and the uCsim simulator. Support for the Single-Core devices will probably come first (as the lack of sp-relative addressing is a serious restriction for the multicore devices, requiring careful though on how to work around it).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 03:35:43 pm
Uhm, I just noticed the PMS150/PMS150C opcodes are different from the PMS154C ones, while still being 14-bit wide. Seems like there are multiple encodings for the same instructions.

For instance:

mov A, 0xAA       -> 0x17AA
mov <addr>, A    -> 0x05C.. something like that
pcadd a               -> 0x0017
wdreset                -> 0x0030

But they're not totally different, most of the time it's just one bit off. Also the PDK fill pattern is 0x1FFF instead of 0x3FFF.

This may need some investigation.

edit: actually no value goes beyond 0x1FFF, I should have noticed that before. Seems like they shaved one bit off and the opcodes are 13-bit (?) if that makes any sense.

There are 3 different instruction sets¹ (each with some minor variation such as possible presence of mul). I assumed them to be 14, 15 and 16 bits. But from what you found it seems that they are 13, 14 and 16 bits. The 13-bit instruction set would be used on devices that have up to 1 kiloword of program memory, the 14-bit instruction set for up to 2 kilowords of program memory. The 16-bit instruction set would then be for larger and multicore devices.

Philipp

¹ According to an email by Padauk.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 19, 2018, 04:49:12 pm
Hi Guys,

Just found this thread. Seems like we've been duplicating some work.

I was planning to develop a PC based simulator to allow code to be quickly
tested and debugged, and also perhaps an STM32 based one which would allow
code to be tested "in circuit" with downloadability and decent debugging
capability. Would also like to eventually include device programming in
the STM32 but I've not looked really looked into it yet.

Here's what I've figured out about the instruction set:
I've added some notes and questions at the end, if anyone can help clarify
these points, please let me know.

The PMS/C150 uses a 13 bit opcode:

00000 101ppppp  MOV       A,io-addr
00000 100ppppp  MOV       io-addr,A
10111 dddddddd  MOV       A,imm-data
00111 11aaaaaa  MOV       A,ram-addr
00101 11aaaaaa  MOV       ram-addr,A
00000 110aaaa1  LDT16     ram-addr-even
00000 110aaaa0  STT16     ram-addr-even
00000 111aaaa1  IDXM      A,ram-addr-even
00000 111aaaa0  IDXM      ram-addr-even,A
01001 11aaaaaa  XCH       ram-addr
00000 00110010  PUSHAF
00000 00110011  POPAF
10000 dddddddd  ADD       A,imm-data
00110 00aaaaaa  ADD       A,ram-addr
00100 00aaaaaa  ADD       ram-addr,a
00000 00010000  ADDC      A
00110 10aaaaaa  ADDC      A,ram-addr
00100 10aaaaaa  ADDC      ram-addr,A
10001 dddddddd  SUB       A,imm-data
00110 01aaaaaa  SUB       A,ram-addr
00100 01aaaaaa  SUB       ram-addr,a
00000 00010001  SUBC      A
00110 11aaaaaa  SUBC      A,ram-addr
00100 11aaaaaa  SUBC      ram-addr,A
01001 00aaaaaa  INC       ram-addr
01001 01aaaaaa  DEC       ram-addr
01001 10aaaaaa  CLEAR     ram-addr
00000 00011010  SR        A
01010 10aaaaaa  SR        ram-addr
00000 00011100  SRC       A
01011 00aaaaaa  SRC       ram-addr
00000 00011011  SL        A
01010 11aaaaaa  SL        ram-addr
00000 00011101  SLC       A
01011 01aaaaaa  SLC       ram-addr
00000 00011110  SWAP      A
10100 dddddddd  AND       A,imm-data
00111 00aaaaaa  AND       A,ram-addr
00101 00aaaaaa  AND       ram-addr,A
10101 dddddddd  OR        A,imm-data
00111 01aaaaaa  OR        A,ram-addr
00101 01aaaaaa  OR        ram-addr,A
10110 dddddddd  XOR       A,imm-data
00111 10aaaaaa  XOR       A,ram-addr
00101 10aaaaaa  XOR       ram-addr,A
00000 011ppppp  XOR       io-addr,A
00000 00011000  NOT       A
01010 00aaaaaa  NOT       ram-addr
00000 00011001  NEG       A
01010 01aaaaaa  NEG       ram-addr
01110 bbbppppp  SET0      io-addr.bit
01111 bbbppppp  SET1      io-addr.bit
00011 bbb0aaaa  SET0      ram-addr.bit
00011 bbb1aaaa  SET1      ram-addr.bit
10010 dddddddd  CEQSN     A,imm-data
01011 10aaaaaa  CEQSN     A,ram-addr
01100 bbbppppp  T0SN      io-addr.bit
01101 bbbppppp  T1SN      io-addr.bit
00010 bbb0aaaa  T0SN      ram-addr.bit
00010 bbb1aaaa  T1SN      ram-addr.bit
00000 00010010  IZSN      A
00000 00010011  DZSN      A
01000 10aaaaaa  IZSN      ram-addr
01000 11aaaaaa  DZSN      ram-addr
110aa aaaaaaaa  GOTO      code-addr
111aa aaaaaaaa  CALL      code-addr
00001 dddddddd  RET       imm-data
00000 00111010  RET
00000 00111011  RETI
00000 00000000  NOP
00000 00010111  PCADD     A
00000 00111000  ENGINT
00000 00111001  DISGINT
00000 00110110  STOPSYS
00000 00110111  STOPEXE
00000 00110101  RESET
00000 00110000  WDRESET
00000 00000000  TRAP     // Assembler accepts, but same as NOP

General notes:
--------------
Full ram-addr range is 0x00-0x3B (60 bytes).

Instructions requiring ram-addr-even allow only 0x00-0x1E, lowest bit
is *NOT* encoded and is assumed to be zero.

Bit set/clear instructions on ram-addr allow only 0x00-0x0F.

Full io-addr range is 0x00-0x1F.


Instruction set notes:
----------------------
According to the data sheet, there are 4 flags: OV, Z, C, AC

Other than 'C' which can be accessed in the ADDC, SUBC, SRC and SLC
instructions, it is not clear what role the OV, Z and AC flags play.
There does not appear to be any instructions which access them.
The only conditionals are "compare ACC" and skip.

The only way I can see to access the other flags is via PUSHAF and then
reading them from memory (you would need to know exactly where SP points).

I'm wondering if this is "cut/paste" error and this processor does not
actually have OV, Z and AC (would make writing the simulator easier).

Perhaps someone with the actual part could write some test code using
arithmetic instructions and PUSHAF to test if these flags are actually
implemented on the PMS150?


The data sheet also says (page 18): (sic)
"The OTP program memory may contains the data, tables and interrupt entry."

I can see no capability in the instruction set to read data/tables from
program memory (other than immediate data).
Perhaps I have missed something?


The instruction set allows for a MAXIMUM of 64 bytes of RAM ... RAM
addresses are encoded in 6 bits. Yet, the indirect instruction IDXM uses
"pointer" values in memory which are two bytes in size. This makes no
sense to me as RAM is a very limited resource, and only one byte is needed
to address all of it. It also wastes instructions clearing the unused top
byte of the pointer - also a limited resource.

Perhaps "special" values in the upper byte allow indexed access to other
things, such as CODE memory or IO space ... but I can find no mention of
any such capability. Anyone know better?


PADAUK assembler notes:
-----------------------
HB@,LB@/HD@,LD@ can be used to access high/low byte of word data:
   MOV A,hb@word_symbol

HA@,LA@ can be used to get high/low symbol address as immediate-data:
   MOV A,ha@symbol

IO. can be used to specify an arbitrary IO address:
   MOV A,io.2

I've not found a prefix for force a RAM access. The only way I've found
to access ROM is by explicitly declaring symbols with "word" and "byte"
directives. Anyone know better?


Regards,
Dave

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 04:57:52 pm
Incidentally, some interesting ISA quirks I've noticed:


So if you wanted C-style stack frames, god help you, your function preamble/postamble would look like:

Code: [Select]
mov a, lb@fp ; read old frame pointer
pushaf ; save
mov a, sp ; read stack pointer
mov fp, a ; set new frame pointer
add A, 8 ; allocate stack frame
mov SP, A ; update stack pointer
...main code here...
mov a, fp ; read current frame pointer
mov sp, a ; retrack over frame
popaf ; load old frame pointer
mov fp, a ; reload old frame pointer
ret
 

Blech.

To read a value from the frame, you'd need:

Code: [Select]
mov a, 4 ; frame offset
add a, fp ; add frame pointer
mov lb@ptr, a
idxm a, ptr

...which is equally grim. Running traditional C on this would be a mug's game, of course.

Cowgol doesn't use stack frames, though, so it's golden.

You might be able to do some incredibly basic Forth, based around an opcode interpreter, with some hoops to jump through to be able to read words out of RAM as well as program memory, but it's probably only worth it for the lols --- I expect it would eat most of the program space and be slow to boot, and with the very limited I/O capability you wouldn't be able to interact with it once you'd done it. Admittedly, running Forth on a 3c machine would make for some pretty serious lols.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 05:05:46 pm
Yay, so much talking across people...

Re data tables: I think they're referring to this sort of thing:

Code: [Select]
; index in A, returns value in A
load_value_from_table:
  pcadd a ; jump to pc + a
  ret 42
  ret 99
  ret -6
  ret 127
  ...etc...

I haven't seen anything for accessing program data. I assume the assembler knows whether to generate an IO or RAM instruction by the type of the symbol you're addressing.

Re the other flags: the flags byte is at IO address 0, so you can test any individual but with t1sn IO.3 or similar. I don't think we can get away with ignoring them...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 19, 2018, 05:12:50 pm
Re the other flags: the flags byte is at IO address 0, so you can test any individual but with t1sn IO.3 or similar. I don't think we can get away with ignoring them...

Thanks, I hadn't picked up on that little detail yet (been busy working out the instructions). That explains it.

Dave
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 05:48:10 pm
Seems like we've been duplicating some work.

I would like to insist on finding a way to better collaborate on this. Something like Slack could help since we would have a decent chat platform to keep everything organized and coordinate stuff. We could have various channels for RE of the programmer, RE of the ISA, tools implementation, etc... would anyone be interested?

Cowgol doesn't use stack frames, though, so it's golden.

Your small language seems really interesting. I also do not see a lot of sense in porting "full" C for this architecture, IMHO it's just less of an hassle to write assembly. A mixed language with assembly+some high level constructs is the best thing, which is in fact what PADAUK did with their Mini-C. If we make an open source toolchain it wouldn't be bad to have our own language for this thing. Of course the self-hosting capability of your compiler (while being really cool) here is pointless, but I see myself liking a language like Cowgol with the possibility to interleave assembly code like PADAUK's Mini-C lets you do. I mean, instead of replicating their Mini-C we could take the opportunity to try something else.

Of course if someone manages to make C compile for this MCUs through SDCC or whatever, that would be really cool, but I would like to see how much overhead it is added, especially regarding function calls.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gslick on November 19, 2018, 05:52:34 pm
Hi Guys,

Just found this thread. Seems like we've been duplicating some work.

I was planning to develop a PC based simulator to allow code to be quickly
tested and debugged, and also perhaps an STM32 based one which would allow
code to be tested "in circuit" with downloadability and decent debugging
capability. Would also like to eventually include device programming in
the STM32 but I've not looked really looked into it yet.

Regards,
Dave

Are you the ImageDisk Dave? Interesting to see you pop up on this thread and looking at these low cost microcontrollers.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 19, 2018, 06:24:31 pm
Hi Dave,

Great that you did the 13 bit instruction set. This is no duplicated work. I did the 154C which uses 14 bit instructions.

Please have a look at the github project I started:

https://github.com/free-pdk

If you like I can add you to the developer list.

Regarding FLAGs:

Have a look at the ".INC" include file in IDE. You can see that IO @ 0x00 holds all the flags:

Code: [Select]
FLAG IO_RW 0x00
OV IO_RW FLAG.3
AC IO_RW FLAG.2
CF IO_RW FLAG.1
ZF IO_RW FLAG.0

So with simple bit tests like T0SN IO.n  and T1SN IO.n you can check and skip next instructions with flags.

Example: To test for OV flag following code can be used:

Code: [Select]
T1SN OV
GOTO OVCLEAR
NOP
NOP
OVCLEAR:

You also could use  T1SN  FLAG.3

In the .INC file you also see that SP is emulated as an IO register and more interesting stuff.


In the next few days I will write a simulator for the 14 bit core. This should not take long at all.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 06:26:48 pm
Your small language seems really interesting. I also do not see a lot of sense in porting "full" C for this architecture, IMHO it's just less of an hassle to write assembly. A mixed language with assembly+some high level constructs is the best thing, which is in fact what PADAUK did with their Mini-C. If we make an open source toolchain it wouldn't be bad to have our own language for this thing. Of course the self-hosting capability of your compiler (while being really cool) here is pointless, but I see myself liking a language like Cowgol with the possibility to interleave assembly code like PADAUK's Mini-C lets you do. I mean, instead of replicating their Mini-C we could take the opportunity to try something else.

Of course if someone manages to make C compile for this MCUs through SDCC or whatever, that would be really cool, but I would like to see how much overhead it is added, especially regarding function calls.

The Padauks aren't the only architecture on which stack access is inefficient. For other such architectures (e.g. MCS-51), SDCC makes functions non-reentrant by default (i.e. unless the function is marked __reentrant or the --stack-auto command-line argument is supplied), placing local variables at fixed memory locations.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 07:13:48 pm
SDCC makes functions non-reentrant by default (i.e. unless the function is marked __reentrant or the --stack-auto command-line argument is supplied), placing local variables at fixed memory locations.

Thanks for telling, I never used SDCC before actually and didn't know it supported even this kind of architectures. Nice to know.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 19, 2018, 07:44:14 pm
By popular demand ;)
https://github.com/mypdk/radare_plugins

Anyhow my idea for a "universal" instruction table was to have a list of objects like this, if this can somehow interest you:

It may be faster than your current approach (which I like anyway, it is very readable IMHO) but by pattern matching like that may not be the most efficient thing, also you'll have to reconstruct the parameter values and other stuff which would be easier with a table like mine, at least that's what I anticipate.

You're absolutely right your instruction table is more precise but it is a lot less generic and requires more work.
My idea was to simply let the computer figure these things out a later point. The basic idea is to have something as easy to read and maintain as possible for these little buggers.
Later a parser can look at the definitions and write something like your structs automatically or generate an optimized assembler/disassembler.

I'm an engineer and thus obligated to be as lazy as possible   :popcorn:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 08:07:48 pm
I'm an engineer and thus obligated to be as lazy as possible   :popcorn:

I'm still not an engineer, just half-way through, so I can still be not lazy sometimes :P

I'm implementing the method I described, currently my table is defined like this:

Code: [Select]
static const auto PMS154_INSTRUCTIONS_SPEC = std::vector<instr_spec_t>
{
  // {mnemonic, opcode, opcode_mask, {args...}}

  {"nop",     0x0000, 0x3FFF, {}},

  {"addc",    0x0060, 0x3FFF, {{Accumulator, 0, 0}}},
  {"subc",    0x0061, 0x3FFF, {{Accumulator, 0, 0}}},
  {"izsn",    0x0062, 0x3FFF, {{Accumulator, 0, 0}}},
  {"izsn",    0x0063, 0x3FFF, {{Accumulator, 0, 0}}},

  // ...

  {"wdreset", 0x0070, 0x3FFF, {}},

  {"pushaf",  0x0072, 0x3FFF, {}},
  {"popaf",   0x0073, 0x3FFF, {}},

  // ...

  {"xor",     0x00C0, 0x3FC0, {{IO, 0, 6}, {Accumulator, 0, 0}}},
  {"mov",     0x0180, 0x3FC0, {{IO, 0, 6}, {Accumulator, 0, 0}}},
  {"mov",     0x01C0, 0x3FC0, {{Accumulator, 0, 0}, {IO, 0, 6}}},

  {"ret",     0x0200, 0x3F00, {{Immediate, 0, 8}}},

  {"stt16",   0x0300, 0x3F81, {{Memory, 0, 7}}},
  {"ldt16",   0x0301, 0x3F81, {{Memory, 0, 7}}},
  {"idxm",    0x0380, 0x3F81, {{Memory, 0, 7}, {Accumulator, 0, 0}}},
  {"idxm",    0x0381, 0x3F81, {{Accumulator, 0, 0}, {Memory, 0, 7}}},

  {"swapc",   0x0400, 0x3E00, {{IO, 0, 6}, {Bit_N, 6, 3}}},

  {"comp",    0x0600, 0x3F80, {{Accumulator, 0, 0}, {Memory, 0, 7}}},
  {"comp",    0x0680, 0x3F80, {{Memory, 0, 7}, {Accumulator, 0, 0}}},
  {"nadd",    0x0700, 0x3F80, {{Accumulator, 0, 0}, {Memory, 0, 7}}},
  {"nadd",    0x0780, 0x3F80, {{Memory, 0, 7}, {Accumulator, 0, 0}}},

  // ...
};

Which I hope you agree is still pretty readable thanks to various new C++ things that allow it to be written like that. Maybe with opcodes written in binary would have been easier but well...

And the hearth of the disassembler code is literally 60 lines of code, for the assembler will just be a little bit more. Once you have such a table you can just iterate over all the table and find whatever matches. If you are disassembling you check the opcode with the mask, if you are assembling you check the mnemonic and the parameters in their respective order. If you need to assemble for a variant of the instruction set you just pass another table.

Anyway I'm following my initial idea to create a "libpdk" which does everything as I previously described. That doesn't mean my approach is orthogonal to what you are doing with radare2, i.e. you could then use the library with the assembling/disassembling capabilities to create the plugin pretty easily just by calling in the library code.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 19, 2018, 08:27:23 pm
Are you the ImageDisk Dave? Interesting to see you pop up on this thread and looking at these low cost microcontrollers.

I am.

Perhaps more relevant to these discussions is my past-life of creating development tools for little processors (mostly 8-bit). C compilers, assemblers, debuggers, simulators etc.
If you're bored, you can look under "sample projects" at www.dunfield.com (http://www.dunfield.com) to see some of the similar/related stuff I used to support myself with.

MCUs in the "few cents" range are an interesting development!

Regards,
Dave

** Mostly retired now, but always up for an interesting project!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 09:00:38 pm
I got a disassembler for the 14-bit ISA working in a preliminary state based on the work that js_12345678_55AA did REing the opcodes. There are some strange things in the code generated by the IDE however, such as:

- sometimes there are calls to 0x07f... which are in the "0x3FFF filled" part of the ROM, 0x3FFF is "call @0x7ff", and at 0x7ff there's "izsn [0x44]" which doesn't make a lot of sense (?)
- there are some opcodes we don't know about, such as 0x0006 or 0x0007
- the code flow doesn't make sense in general in some cases, for instance the "GOTO FPPA0 instruction" at 0x0001 (I'm reading from the datasheet of the PMS154C) is "goto @0xc", at that address there's some code that then calls @0x7f6 which doesn't make sense, shouldn't the user program start?

I can however locate the code I wrote. The void func(void) is at 0x0002 till 0x000b and the FPPA0 is at 0x0086 (there's a goto going there at 0x0013).

This is the code I compiled from the IDE

Code: [Select]
#include "extern.h"

void func(void)
{
byte x = 5;
byte y = 6;
byte c;

c = x + y - ~x;
}

void FPPA0 (void)
{
.ADJUST_IC SYSCLK=IHRC/2 // SYSCLK=IHRC/2

func();

byte c = 0;

while (1)
{
c++;
}
}

I attacched the disassembled ROM if someone wants to take a look.

Has someone figured out this stuff yet? I guess there's most likely something wrong with the opcodes RE, but IDK, I still have to take a look. I'm posting so that anyone can check if interested.

edit: just realized the 0x0006 and 0x0007 where the undocumented instructions js_12345678_55AA found https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1970672/#msg1970672 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1970672/#msg1970672) , makes sense
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 19, 2018, 09:12:02 pm
Hi,

@gdelazzari

Read about how IDE / WRITER inserts the "rolling code" (is in help / manual of IDE).

For 154 the example says to read the serial numer / rolling code by this:
Code: [Select]
call _SYS(ADR.ROLL);
call _SYS(ADR.ROLL)+1;
call _SYS(ADR.ROLL)+2;

Writer will insert "RET 0xAB  RET 0xCD  RET =0xEF" at those addresses which are located at the end of the ROM.

One call I could not figure out is to (last instruction possible -1) 0x3FFE. Maybe Writer will insert another RET 0x12  there.

I need to wait for my writer to arrive so I can write and read back.

The very last ROM word contains the values to setup IHRC , Security Fuse, ... (everything you setup with .ADJUST_IC).

.ADJUST_IC also will put a lot of init code inside (even contains delay loops, in case you setup something for SYSCLK other than "DISABLED").



Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 09:22:14 pm
Thanks, this now makes more sense. By the way I have my disassembler implemented with an instruction table like the one I posted before which I believe is a pretty flexible approach, adding an assembler and an emulator based on that should be pretty easy. I'm sure you're almost there to a complete disassembler too (and maybe other tools). What approach did you use? I'm trying to understand if my code could be useful or not, I guess I'll wait for you to upload your disassembler to the GitHub org?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 19, 2018, 09:36:00 pm
I try to build a cycle accurate simulator which is ultra fast and can synchronize to real time (even on STM32 :-)). I took some inspiration from already existing tiny fast 6502 simulators.

Right now I try to figure out (imagine) how the AC and OV flags are set. The user manual of the processors does not describe it in an understandable way for me.


Here is a part of the source of already finished code for some opcodes (eA holds A, ePC the PC, eF the FLAGs, eSP the SP)

Code: [Select]
  uint8_t  eF = CPUioGet(0x00);             //get flags from emulated IO port, mapped like in IO flags: (- - - - V A C Z)
  uint8_t  eSP = CPUioGet(0x02);            //get SP from emulated IO port
  uint16_t opcode = CPUcodeGet( ePC++ );    //fetch next opcode and advance PC
  eCurrentCycle++;                          //increment current cycle counter

  if( 0x3FFE == opcode ) //special opcode ?
  {
    //TODO... find out what it does. IDE inserts when using ADJUST_CHIP
  }
  else
  //14 bit opcodes 0x0000 - 0x00BF
  if( opcode<=0x00BF )
  {
    switch( opcode )
    {
      case 0x0000: break; //NOP

      ...
  }
  ...
  else
  //6 bit opcodes 0x02.. , 0x2800 - 0x2FFF
  if( (0x0200 == (opcode&0x3F00)) || (0x2800 == (opcode&0x3800)) )
  {
    switch( opcode & 0x3F00 )
    {
      case 0x0200: eA = opcode&0xFF; ePC=(((uint16_t)CPUmemGet(--eSP))<<8); ePC|=CPUmemGet(--eSP); break; //RET k
 
      case 0x2800: eA += opcode&0xFF; eF=(eA>255)<<1;eA&=0xFF;eF|=!eA; break; //ADD A,k //TODO: OV, AC
      case 0x2900: eA -= opcode&0xFF; eF=(eA>=0)<<1;eA&=0xFF;eF|=!eA; break; //SUB A,k //TODO: OV, AC

      case 0x2A00: //CEQSN A,k
      case 0x2B00: //CNEQSN A,k
        T = eA-(opcode&0xFF);            //TODO: A-k or k-A ?
        if( ((0x2A00==(opcode&0x3F00)) && !T) ||
            ((0x2B00==(opcode&0x3F00)) && T) )
        {
          ePC++; eCurrentCycle++;
        }
        eF=(T>255)<<1;T&=0xFF;eF|=!T; //TODO: OV,AC (based on T)
        break;

      case 0x2C00: eA &= opcode&0xFF; eF&=~1;eF|=!eA; break; //AND A,k
      case 0x2D00: eA |= opcode&0xFF; eF&=~1;eF|=!eA; break; //OR A,k
      case 0x2E00: eA ^= opcode&0xFF; eF&=~1;eF|=!eA; break; //XOR A,k
      case 0x2F00: eA  = opcode&0xFF; break; //MOV A,k
    }
  }               
  else
  //5 bit opcodes 0x0400 - 0x0500, 0x1800 - 0x27FF
  if( (0x0400 == (opcode&0x3E00)) || ((opcode>=0x1800) && (opcode<=0x27FF)) )
  {
    uint8_t bit = 1<<((opcode>>6)&7);
    uint8_t addr = opcode&0x3F;
    switch( opcode & 0x3E00 )
    {
      case 0x0400: T=CPUioGet(addr);CPUioPut(addr,eF&2?T|bit:T&~bit); eF&=~2;eF|=(T&bit)?2:0; break; //SWAPC IO.n
      case 0x1800: if( !(CPUioGet(addr)&bit) ) { ePC++; eCurrentCycle++; } break;                    //T0SN IO.n
      case 0x1A00: if( CPUioGet(addr)&bit ) { ePC++; eCurrentCycle++; } break;                       //T1SN IO.n
      case 0x1C00: CPUioPut(addr,CPUioGet(addr)&~bit); break;                                        //SET0 IO.n
      case 0x1E00: CPUioPut(addr,CPUioGet(addr)|bit); break;                                         //SET1 IO.n
      case 0x2000: if( !(CPUmemGet(addr)&bit) ) { ePC++; eCurrentCycle++; } break;                   //T0SN M.n
      case 0x2200: if( CPUmemGet(addr)&bit ) { ePC++; eCurrentCycle++; } break;                      //T1SN M.n
      case 0x2400: CPUmemPut(addr,CPUmemGet(addr)&~bit);break;                                       //SET0 M.n
      case 0x2600: CPUmemPut(addr,CPUmemGet(addr)|bit);break;                                        //SET1 M.n
    }
  }
  else
  //3 bit opcodes 0x3000 - 0x3FFF
  if( (0x3000 == (opcode&0x3000)) )
  {

    if( opcode & 0x0800 ) //CALL needs to put current PC on stack
    {
      CPUmemPut( eSP++, ePC & 0xFF ); //TODO: check if on stack is little endian
      CPUmemPut( eSP++, ePC>>8 );     //TODO: check if on stack is little endian
    }
    eCurrentCycle++;
    ePC = opcode & 0x07FF;
  }
  else
  {
    //unknown instruction
    CPUexceptionEmulation("Unknown instruction", opcode );
  }

  CPUioPut(0x02,eSP);  //store SP to emulated IO port
  CPUioPut(0x00,eF);   //store flags to emulated IO port

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 09:40:18 pm
Is there any possibility of there being an internal ROM with more code in it? That would explain the weird jumps and calls.

Do any of these things have SPI or I2C? Because if we ever figure out the programming protocol, and you could make one of these processors program another, you could incredibly cheaply build a hypercube cluster of the flash versions of these things, all bootstrapped from one processor at the corner attached to the outside world... it'd be useless, but fascinating. Sadly, without some sort of fast comms it's probably not worth it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 19, 2018, 09:54:00 pm
If you are seeking for really fast emulation, why not a lookup table of function pointers? Keep in mind that, since it's an harvard architecture + OTP + no way to read raw data from ROM, it is feasible to pre-process the ROM code as you wish if that helps you encode the instructions in such a way that results in a faster interpretation, given you don't need the original content for other purposes other than interpreting the code.

For instance (just writing down what is passing through my mind right now, will need a lot of refinement, but the idea is this):

- map each instruction to an id (arbitrarly, whatever order you like) starting from 0 to the num of instr-1 so you can have a C array of pointers to functions that execute the instruction
- preprocess the ROM by "disassembling" the 14-bits or whatever-bits opcodes and representing them, for instance, as 3 bytes: one for the id, one for the first parameter and one for the second (if any)
- loop over the processed ROM and lookup the corresponding emulation function like instr_funcs[instr_id]();, place the two parameters in a couple of globals or just let the emulation functions pick them up relative to the PC (which is global ofc)
- the emulated function does it stuff and returns

not sure how to cleanly handle cycle-accurate though, I'll have to think about that.

This may be a bit slower than your fastest if (opcode ...) evaluation, but you gain a constant and predictable time for all instructions, which I think is preferrable especially if the code that runs a cycle of the emulated CPU is inside an interrupt handler which fires at <x> MHz. All of this is assuming you're not on Cortex-M7 i.e. there's no cache in between, that messes everything up obviously.

Another (reeeeeally cool) thing to do would be JIT, I have no idea if that could be feasible given how different the architectures are, and of course you would lock yourself to ARM Cortex, but that would be indeed really cool.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 10:12:10 pm
Is there any possibility of there being an internal ROM with more code in it? That would explain the weird jumps and calls.

Do any of these things have SPI or I2C? Because if we ever figure out the programming protocol, and you could make one of these processors program another, you could incredibly cheaply build a hypercube cluster of the flash versions of these things, all bootstrapped from one processor at the corner attached to the outside world... it'd be useless, but fascinating. Sadly, without some sort of fast comms it's probably not worth it.

The is a reserevd are of, depeding on the device 8 to 32 words at the end of the ROM. Not a place to hide a lot of code, but, as already explained (and stated in the documentation) for checksums, rolling code, oscillator calibration data, code options. Since the 13-bit and 14-bit instruction sets do not have the ltabh and ltabl instructions, on those devies the rollign code is implemented as ret k instruction. You jump into the code, immediately jump back, and get the data byte in the accumulator.

The devices do not have I²C or SPI. But it can easily be emulated in software. That's actually one of the good things about the multicore design: You let one core handle some I/O protocol, and another core handles your normal program. IMO, this can be a good alternative to hardware peripherals. It makes the hardware simpler, cheaper, and all the gates can be used for the tasks at hand, instead of many of them sitting idle.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 10:14:24 pm
Perhaps more relevant to these discussions is my past-life of creating development tools for little processors (mostly 8-bit). C compilers, assemblers, debuggers, simulators etc.
[…]
** Mostly retired now, but always up for an interesting project!

Would you be interested in contributing to SDCC, a free C compiler targeting small devices? There is a bit of a lack of developers and developer time recently. SDCC is still progressing, but some backends have fallen a bit behind (and of course there is work to do in the frontend, too).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 10:36:27 pm
Wait, are you the Dunfield C Dunfield?

I think way back when when I was looking for a portable C compiler I kept running into your C page and thinking it looked ideal and then cursing its closed source-ness... then Amsterdam Compiler Kit got open sourced, and it was so awful to build I begged a copy of the source repository from Ceriel Jacobs, uploaded it to SourceForge, and became the maintainer for it. (I think I now have the oldest genuine timestamps on github.)

With modern eyes I see now that Micro-C is K&R, so it wouldn't have been any good to me back then, but it's still amazingly small. If you're ever thinking of releasing the source I'd be fascinated to see how it works. (Cowgol's a lot larger, and I needed to split it into eight different compiler passes to make it run on a 6502...)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 19, 2018, 10:56:31 pm
Padauk is not making any money selling the programmer, so why don't ask them for the programming protocol?
The have been asked and they refused to provide any information.

It could make sense to reverese-engineer the protocol for the Flash-based devices first:

1) These devices are probably more interesting to us than the OTP ones
2) The protocol is simpler (less voltages, max 8V on ICVPP)
3) The pins used are documented with signal names (VDD, GND, ICVPP, ICPDA, ICPCK)

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: david.given on November 19, 2018, 11:49:52 pm
I don't know if the protocol's the same, but ICPCK/ICPDA are the same names that Holtek use for their line of ludicrously cheap microcontrollers.

http://www.holtek.com/documents/10179/106680/Holtek_Flash_MCU_Quick_Start_Guide_V100_en.pdf (http://www.holtek.com/documents/10179/106680/Holtek_Flash_MCU_Quick_Start_Guide_V100_en.pdf)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 20, 2018, 03:34:45 pm
Would you be interested in contributing to SDCC, a free C compiler targeting small devices?

Probably not, I've not seen much open-source code I'd be happy working on... but that's a different discussion.


Wait, are you the Dunfield C Dunfield?

Mea culpa!

Regarding the source, I've not made it publicly available, but I've been known to give it out to interested parties.

For things not pertaining to the Padauk discussion, please contact me off list. Either through the messaging here (I'll try to check it at least every couple of days), or to my email at:

  my-first-name{dot}my-last-name{@}gmail{dot}com


Regarding simulation:

With modern tools, "switch" can be as efficient as a function call table, and you can avoid the overhead of functions entry/exit on each instruction (which can be several instructions to establish and release a stack frame).

I find the most difficult part doing the flags... C has a disadvantage of not having visibility to the processor flags, so when coding a simulator in C you need to work out the flag updates manually. This is usually more operations than performing the main operation of the simulated instruction.

Back in the day, when PC's were not a whole lot faster than the embedded systems we were emulating, I coded the simulation functions in assembly language, where I could reduce decoding to a very simple jump table, and access the flags set by the operation directly (which are usually at least similar to the setting of flags on the target processor.

My EMILY52 simulator could emulate an 8051/52 in real time on a Pentium1 (or even a decent 486). The simulation engine was coded in 8086 assembly and had an advantage that the 8051 flags were very similar to the 8086 flags. Instruction that didn't set flags would jump directly back to the next decode, instructions which set flags jumped to one of several routines which saved the flags in question (I think there were 3 or 4 different combinations of flags set by instructions) before heading on back to the next decode.

For instructions which used the flags, I simply loaded the 8086 flags from the saved flags before executing the instruction. When the flags were read as a byte, I used a lookup table to translate the saved 8086 flags into the corresponding 8051 flags positions.

8051 registers were only saved/restored to 8086 registers when the simulation stopped or started ... while running, they resided in 8086 registers and did not have to be loaded "per instruction".

Thing ran fast! - on more modern systems, it runs considerably faster than a hardware 805x ... It was so "streamlined" that the simulation engine had no "test for exit" .. just a tight instruction decode loop. When the user hit "STOP" I would plant a JMP instruction into the loop to break it which was then patched back by the exit handler.

Another technique I've used in the past to achieve high-speed simulation, which works well if:
 1) You can live with variance in the speed the first time a block of code gets executed,
 2) You don't support or accept higher overhead for self-modifying code

Is to have an array of JMP targets for every address (easy if you processor has 1024 words of code memory, harder if it has megs)... At the beginning, each JMP targets a routine which decodes the instruction and updates the JMP target to point to the handler for that instruction before launching it.

On subsequent passes the JMP branches directly to the correct instruction handler, and never even has to look at the opcode.

This is particularity effective if the opcodes are complex to decode words. For simple opcodes, a simple JMP table will be nearly as fast and much simpler to debug.


On a PC I'd probably use a simple JMP table for the PMS150, 13 bit = 8k words (32k bytes) and would give you one simple direct jump to the correct handler.

On the STM with 64K of code, 32K would be a bit much, I'd probably divide the opcodes into blocks based on which bits are used and decode with ANDs and a few switches.

But I haven't really looked into it that far yet...

Dave


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 21, 2018, 09:11:58 pm
Hi,

I disassembled and commented the code which the IDE inserts at the start of the OTP.

This code is used for calibration of the internal high speed RC oscillator.

It looks like WRITER is doing the following:

1. write the complete OTP and set the calibration value to 0xFF (actually a RET 0xFF)
2. reset the IC and wait for IC to execute the calibration measurement program (handshake and bit bang protocol using WRITER_CLK:PA.3 / WRITER_DAT_OUT:PA.5 / WRITER_DAT_IN:PA.6)
3. write the calibration value over the 0xFF value

=> This is a trick. The OTP is intial all '1'. Programing can change a '1' to a '0' ... but never back to one. So writing 0xFF leaves this cell all '1' and later when the real value is present it can be written there.

As you can see the (quite big) calibration code wastes some valuable OTP.
There is also a small programing mistake inside (near the end of the calibration)  8). ==> @PADAUK: maybe you want to fix it :-) (the mistake is harmless since WRITER can just reset the IC in order to restart a calibration, again ==> @PADAUK: you can save some valuable space here by just removing instructions from 0x004F - 0x0052)
With a little bit of practice the code also could be stripped here and there. Something we can do in future  :)


0x0000:   0x0070    WDRESET                     ;reset watchdog

0x0001:   0x2f00    MOV A, 0x00     
0x0002:   0x0182    MOV IO(0x02), A  ;SP        ;set SP to memory start (0)

0x0003:   0x3fed    CALL 0x7ED                  ;get IHRCR (value inserted from WRITER)
0x0004:   0x018b    MOV IO(0x0B), A  ;IHRCR     ;setup IHRCR

0x0005:   0x3fee    CALL 0x7EE
0x0006:   0x019a    MOV IO(0x1A), A             ;BGTR? (not in datasheet)

0x0007:   0x2f00    MOV A, 0x00                 ;setup low voltage detector (value inserted from IDE .CHIP)
0x0008:   0x019b    MOV IO(0x1B), A             ;MISC_LVR 4V/3V5/3V/2V75/2V5/1V8/2V2/2V

0x0009:   0x2f34    MOV A, 0x34     
0x000a:   0x0183    MOV IO(0x03), A  ;CLKMD     ;setup clock mode (value inserted from IDE .ADJUST_IC)

0x000b:   0x3ffe    CALL 0x7FE                  ;get stored calibration value (stored during programing of OTP)

;This is a nice trick. The OTP reads all as '1' when not programmed. Programing will change the relevant bits to '0'.
;The trick is that you can program the OTP multiple times. It is always possible to change '1' to '0' but never the other way around.
;So they store 0x02FF in code memory at position 0x7FE which translates to RET 0xFF. Later programer can change the 0xFF return value by
;overwriting it with the final value (0xFF still all bits '1').
;This means all the code follows is used for calibration during programing only (big waste of OTP)

0x000c:   0x2aff    CEQSN A, 0xFF               ;Check if is 0xFF (nothing written there?)
0x000d:   0x3054    GOTO 0x054                  ;Jump over calibration routine to user program

0x000e:   0x3fed    CALL 0x7ED                  ;get IHRCR (value inserted from programmer)
0x000f:   0x0b81    MOV [0x01], A               ;store it in memory @0x01

0x0010:   0x1f91    SET1 IO(0x11).6  ;PAC.6     ;configure PA.6 as output

;calibration routine
0x0011:   0x2f20    MOV A, 0x20     
0x0012:   0x0b80    MOV [0x00], A               ;store 0x20 in memory @0x00

0x0013:   0x1ad0    T1SN IO(0x10).3  ;PA.3      ;check for HIGH signal at PA.3   <-- check for handshake signal for WRITER
0x0014:   0x3013    GOTO 0x013                  ;wait until PA.3 is high

0x0015:   0x1f90    SET1 IO(0x10).6  ;PA.6      ;set PA.6 to HIGH                <-- send response to WRITER

0x0016:   0x0063    DZSN A                      ;1c big delay, underflows after first loop
0x0017:   0x3016    GOTO 0x016                  ;2c inner loop apx. 3*256 cycles = 768 cycles
0x0018:   0x1180    DZSN [0x00]                 ;1c
0x0019:   0x3016    GOTO 0x016                  ;2c outer loop apx. 32*(768+3) = 24672 cycles,
                                                ;-224 cycles from first inner loop (was init with 32 instead of 255) = 24448 cycles total delay

0x001a:   0x1d90    SET0 IO(0x10).6  ;PA.6      ;set PA.6 to LOW                 <-- stop sending response to WRITER

0x001b:   0x18d0    T0SN IO(0x10).3  ;PA.3      ;check for LOW signal at PA.3    <-- wait for WRITER to stop sending handshake signal
0x001c:   0x301b    GOTO 0x01B                  ;wait until PA.3 is low

0x001d:   0x2f01    MOV A, 0x01     
0x001e:   0x1950    T0SN IO(0x10).5  ;PA.5      ;if PA.5 is LOW ==> A=0x01 , HIGH ==> A=0xFF <-- WRITER sets ? ? ? value to 1/255 by setting PA.5
0x001f:   0x2fff    MOV A, 0xFF     

0x0020:   0x0c01    ADD A, [0x01]               ;add to IHRCR (value inserted from programmer) 1 or 255 (see above)
0x0021:   0x018b    MOV IO(0x0B), A  ;IHRCR     ;set new IHRCR
0x0022:   0x0b81    MOV [0x01], A               ;store new IHRCR value in memory @0x01

0x0023:   0x1ad0    T1SN IO(0x10).3  ;PA.3      ;check for HIGH signal at PA.3   <-- check for handshake signal for WRITER
0x0024:   0x3023    GOTO 0x023                  ;wait until PA.3 is high

0x0025:   0x1b50    T1SN IO(0x10).5  ;PA.5      ;check for HIGH signal at PA.5   <-- WRITER signals all done?
0x0026:   0x304f    GOTO 0x04F                  ;jump to end of calibration code

0x0027:   0x2f04    MOV A, 0x04     
0x0028:   0x0188    MOV IO(0x08), A  ;MISC      ;disable low voltage detector

0x0029:   0x18d0    T0SN IO(0x10).3  ;PA.3      ;check for LOW signal at PA.3    <-- wait for WRITER to stop sending handshake signal
0x002a:   0x3029    GOTO 0x029                  ;wait until PA.3 is low

;start measurment
0x002b:   0x2f02    MOV A, 0x02
0x002c:   0x0182    MOV IO(0x02), A  ;SP        ;setup SP to memory @0x02

0x002d:   0x1304    CLEAR [0x04]                ;zero memory @0x04
0x002e:   0x1305    CLEAR [0x05]                ;zero memory @0x05
0x002f:   0x2f55    MOV A, 0x55
0x0030:   0x0b82    MOV [0x02], A               ;store 0x55 in memory @0x02
0x0031:   0x2f00    MOV A, 0x00     
0x0032:   0x0b83    MOV [0x03], A               ;store 0x00 in memory @0x03

;16 bit loop (0x0055) times some operations with internal value LDSPTL:LDSPTH (timing register?)
0x0033:   0x0006    LDSPTL                      ;?load from timing register L
0x0034:   0x0b04    XOR [0x04], A
0x0035:   0x0007    LDSPTH                      ;?load from timing register H
0x0036:   0x0805    ADD [0x05], A

0x0037:   0x1584    SL [0x04]                   ;rotate left 16 bit value
0x0038:   0x1685    SLC [0x05]
0x0039:   0x1004    ADDC [0x04]

0x003a:   0x1282    DECM [0x02]                 ;memory low byte -1
0x003b:   0x1083    SUBC [0x03]                 ;memory high byte -1 if carry set
0x003c:   0x1a40    T1SN IO(0x00).1  ;FLAG.CF   ;test for carry (0x0000 -1 => carry set)
0x003d:   0x3033    GOTO 0x033                  ;loop

0x003e:   0x1f90    SET1 IO(0x10).6  ;PA.6      ;set PA.6 to HIGH                <-- send response to WRITER (measurement finished)


;send bit by bit the 16 bit measured value
0x003f:   0x1ad0    T1SN IO(0x10).3  ;PA.3      ;check for HIGH signal at PA.3   <-- check for handshake signal for WRITER
0x0040:   0x303f    GOTO 0x03F                  ;wait until PA.3 is high

0x0041:   0x1584    SL [0x04]                   ;16 bit shift left
0x0042:   0x1685    SLC [0x05]

0x0043:   0x0590    SWAPC IO(0x10).6 ;PA.6      ;set PA.6 according to carry (highest bit from 16 bit value before shift)

0x0044:   0x18d0    T0SN IO(0x10).3  ;PA.3      ;check for LOW signal at PA.3    <-- wait for WRITER to stop sending handshake signal
0x0045:   0x3044    GOTO 0x044                  ;wait until PA.3 is low

0x0046:   0x1950    T0SN IO(0x10).5  ;PA.5      ;check if PA.5 is LOW            <-- WRITER signals to send next bit
0x0047:   0x303f    GOTO 0x03F


0x0048:   0x1d90    SET0 IO(0x10).6  ;PA.6      ;set PA.6 to LOW

0x0049:   0x1ad0    T1SN IO(0x10).3  ;PA.3      ;check for HIGH signal at PA.3   <-- check for handshake signal for WRITER
0x004a:   0x3049    GOTO 0x049                  ;wait until PA.3 is high

0x004b:   0x18d0    T0SN IO(0x10).3  ;PA.3      ;check for LOW signal at PA.3    <-- wait for WRITER to stop sending handshake signal
0x004c:   0x304b    GOTO 0x04B                  ;wait until PA.3 is low

0x004d:   0x1b50    T1SN IO(0x10).5  ;PA.5      ;check for HIGH signal at PA.5   <-- WRITER signals to redo measurement
0x004e:   0x302b    GOTO 0x02B                  ;if PA.5 is LOW do the measurement again

;here seems to be an error in the program from PADAUK, very unlikely PA.3 went hight during last 2 instructions, should be HIGH check for sure
0x004f:   0x18d0    T0SN IO(0x10).3  ;PA.3      ;check for LOW signal at PA.3
0x0050:   0x304f    GOTO 0x04F                  ;wait until PA.3 is low

0x0051:   0x1b50    T1SN IO(0x10).5  ;PA.5      ;check for HIGH signal at PA.5   <-- WRITER signals all done?
0x0052:   0x3011    GOTO 0x011                  ;if PA.5 is LOW do the complete calibration again (including all handshakes)

0x0053:   0x3053    GOTO 0x053                  ;calibration successful, endless loop (chip needs reset + writing of calibration value from WRITER)

;----------------------------------------------------------------------------------------------------------------------------------------------

0x0054:   0x018b    MOV IO(0x0B), A  ;IHRCR     ;normal program start, set IHRCR

0x0055:   0x3055    GOTO 0x055                  ;the user program (was just a "while(1){}" loop)


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 21, 2018, 09:37:49 pm
Nice job js_12345678_55AA, really interesting. Will take an in depth look.

At the moment I also got the 13-bit ISA implemented in my infrastructure so I can disassemble PMS150 (C) ROMs. I noticed an interesting thing (I still have to look at the disasm). The PMS150 (without the C) has an order of magnitude less init code compared to the PMS150C (which seems to have code that more or less does the same stuff the 154C is doing).

I'm attaching the two listings if someone wants to take a look and start figuring it out.

(to discriminate what's "my" code and PADAUK's code, in both ROMs I only have the main which is simply incrementing a byte in memory, you'll find the inc [0x...]; goto @0x... as the last two instructions in both listings, that are the only two things not part of the init code)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 22, 2018, 12:02:57 am
After checking the disassembly of the calibration again some things look suspicious:


;start measurment
0x002b:   0x2f02    MOV A, 0x02
0x002c:   0x0182    MOV IO(0x02), A  ;SP        ;setup SP to memory @0x02

0x002d:   0x1304    CLEAR [0x04]                ;zero memory @0x04
0x002e:   0x1305    CLEAR [0x05]                ;zero memory @0x05
0x002f:   0x2f55    MOV A, 0x55
0x0030:   0x0b82    MOV [0x02], A               ;store 0x55 in memory @0x02
0x0031:   0x2f00    MOV A, 0x00     
0x0032:   0x0b83    MOV [0x03], A               ;store 0x00 in memory @0x03

;16 bit loop (0x0055) times some operations
0x0033:   0x0006    LDSPTL                      ;load from memory where SP is pointing to A
0x0034:   0x0b04    XOR [0x04], A
0x0035:   0x0007    LDSPTH                      ;load from memory where SP is pointing to A
0x0036:   0x0805    ADD [0x05], A

0x0037:   0x1584    SL [0x04]                   ;rotate left 16 bit value
0x0038:   0x1685    SLC [0x05]
0x0039:   0x1004    ADDC [0x04]

0x003a:   0x1282    DECM [0x02]                 ;memory low byte -1
0x003b:   0x1083    SUBC [0x03]                 ;memory high byte -1 if carry set
0x003c:   0x1a40    T1SN IO(0x00).1  ;FLAG.CF   ;test for carry (0x0000 -1 => carry set)
0x003d:   0x3033    GOTO 0x033                  ;loop


At the beginning the SP is setup to point to a new location. SP / stack is never used anywhere after this point in calibration program.
So the only use could be from the undocumented instructions LDSPTL and LDSPTH. Also SP points to the memory which is initialized
with static values.

This lets me think LDSPTL/LDSPTL stands for "LoaD from SP Table Low" / "LoaD from SP Table High":
  LDSPTL   =>   A = [SP]
  LDSPTH   =>   A = [SP+1]

Then the above loop would be again some "obfuscation" crypto from PADAUK (XOR 0x55 ... smells like the magic value they love, known from IDE obfuscation).

The result in this case is just 0x11E4 which is then sent out via bitbang to the WRITER to "verify"  :-DD

The loop also serves the purpose to run for several cycles, so WRITER can measure the time it takes and use it for calibration.


JS

EDIT: The loop runs for exact 1040 cycles (including loop init)  :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: amyk on November 22, 2018, 03:54:49 am
I sorted the 13-bit instructions in opcode order; some interesting patterns emerge (notice ADD SUB ADDC SUBC AND OR XOR MOV), as well as possible present-but-undocumented instructions:

Code: [Select]
00000 00000000  NOP
00000 00000000  TRAP     // Assembler accepts, but same as NOP
00000 00000001
 ..      ..     ??
00000 00001111
00000 00010000  ADDC      A
00000 00010001  SUBC      A
00000 00010010  IZSN      A
00000 00010011  DZSN      A
00000 00010100
 ..      ..     ??
00000 00010110
00000 00010111  PCADD     A
00000 00011000  NOT       A
00000 00011001  NEG       A
00000 00011010  SR        A
00000 00011011  SL        A
00000 00011100  SRC       A
00000 00011101  SLC       A
00000 00011110  SWAP      A
00000 00011111
 ..      ..     ??
00000 00101111
00000 00110000  WDRESET
00000 00110001  ?
00000 00110010  PUSHAF
00000 00110011  POPAF
00000 00110100  ?
00000 00110101  RESET
00000 00110110  STOPSYS
00000 00110111  STOPEXE
00000 00111000  ENGINT
00000 00111001  DISGINT
00000 00111010  RET
00000 00111011  RETI
00000 00111100
 ..      ..     ??
00000 01011111
00000 011ppppp  XOR       io-addr,A
00000 100ppppp  MOV       io-addr,A
00000 101ppppp  MOV       A,io-addr
00000 110aaaa0  STT16     ram-addr-even
00000 110aaaa1  LDT16     ram-addr-even
00000 111aaaa0  IDXM      ram-addr-even,A
00000 111aaaa1  IDXM      A,ram-addr-even
00001 dddddddd  RET       imm-data
00010 bbb0aaaa  T0SN      ram-addr.bit
00010 bbb1aaaa  T1SN      ram-addr.bit
00011 bbb0aaaa  SET0      ram-addr.bit
00011 bbb1aaaa  SET1      ram-addr.bit
00100 00aaaaaa  ADD       ram-addr,a
00100 01aaaaaa  SUB       ram-addr,a
00100 10aaaaaa  ADDC      ram-addr,A
00100 11aaaaaa  SUBC      ram-addr,A
00101 00aaaaaa  AND       ram-addr,A
00101 01aaaaaa  OR        ram-addr,A
00101 10aaaaaa  XOR       ram-addr,A
00101 11aaaaaa  MOV       ram-addr,A
00110 00aaaaaa  ADD       A,ram-addr
00110 01aaaaaa  SUB       A,ram-addr
00110 10aaaaaa  ADDC      A,ram-addr
00110 11aaaaaa  SUBC      A,ram-addr
00111 00aaaaaa  AND       A,ram-addr
00111 01aaaaaa  OR        A,ram-addr
00111 10aaaaaa  XOR       A,ram-addr
00111 11aaaaaa  MOV       A,ram-addr
01000 00000000
 ..      ..     ??
01000 01111111
01000 10aaaaaa  IZSN      ram-addr
01000 11aaaaaa  DZSN      ram-addr
01001 00aaaaaa  INC       ram-addr
01001 01aaaaaa  DEC       ram-addr
01001 10aaaaaa  CLEAR     ram-addr
01001 11aaaaaa  XCH       ram-addr
01010 00aaaaaa  NOT       ram-addr
01010 01aaaaaa  NEG       ram-addr
01010 10aaaaaa  SR        ram-addr
01010 11aaaaaa  SL        ram-addr
01011 00aaaaaa  SRC       ram-addr
01011 01aaaaaa  SLC       ram-addr
01011 10aaaaaa  CEQSN     A,ram-addr
01011 11000000
 ..      ..     ??
01011 11111111
01100 bbbppppp  T0SN      io-addr.bit
01101 bbbppppp  T1SN      io-addr.bit
01110 bbbppppp  SET0      io-addr.bit
01111 bbbppppp  SET1      io-addr.bit
10000 dddddddd  ADD       A,imm-data
10001 dddddddd  SUB       A,imm-data
10010 dddddddd  CEQSN     A,imm-data
10011 00000000
 ..      ..     ??
10011 11111111
10100 dddddddd  AND       A,imm-data
10101 dddddddd  OR        A,imm-data
10110 dddddddd  XOR       A,imm-data
10111 dddddddd  MOV       A,imm-data
110aa aaaaaaaa  GOTO      code-addr
111aa aaaaaaaa  CALL      code-addr
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 22, 2018, 06:51:54 am
Nice job js_12345678_55AA, really interesting. Will take an in depth look.

At the moment I also got the 13-bit ISA implemented in my infrastructure so I can disassemble PMS150 (C) ROMs. I noticed an interesting thing (I still have to look at the disasm). The PMS150 (without the C) has an order of magnitude less init code compared to the PMS150C (which seems to have code that more or less does the same stuff the 154C is doing).

I'm attaching the two listings if someone wants to take a look and start figuring it out.

(to discriminate what's "my" code and PADAUK's code, in both ROMs I only have the main which is simply incrementing a byte in memory, you'll find the inc [0x...]; goto @0x... as the last two instructions in both listings, that are the only two things not part of the init code)

Could you also add the 13-bit instructions to the documentation on GitHub?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 22, 2018, 06:56:36 am
After checking the disassembly of the calibration again some things look suspicious:


;start measurment
0x002b:   0x2f02    MOV A, 0x02
0x002c:   0x0182    MOV IO(0x02), A  ;SP        ;setup SP to memory @0x02

0x002d:   0x1304    CLEAR [0x04]                ;zero memory @0x04
0x002e:   0x1305    CLEAR [0x05]                ;zero memory @0x05
0x002f:   0x2f55    MOV A, 0x55
0x0030:   0x0b82    MOV [0x02], A               ;store 0x55 in memory @0x02
0x0031:   0x2f00    MOV A, 0x00     
0x0032:   0x0b83    MOV [0x03], A               ;store 0x00 in memory @0x03

;16 bit loop (0x0055) times some operations
0x0033:   0x0006    LDSPTL                      ;load from memory where SP is pointing to A
0x0034:   0x0b04    XOR [0x04], A
0x0035:   0x0007    LDSPTH                      ;load from memory where SP is pointing to A
0x0036:   0x0805    ADD [0x05], A

0x0037:   0x1584    SL [0x04]                   ;rotate left 16 bit value
0x0038:   0x1685    SLC [0x05]
0x0039:   0x1004    ADDC [0x04]

0x003a:   0x1282    DECM [0x02]                 ;memory low byte -1
0x003b:   0x1083    SUBC [0x03]                 ;memory high byte -1 if carry set
0x003c:   0x1a40    T1SN IO(0x00).1  ;FLAG.CF   ;test for carry (0x0000 -1 => carry set)
0x003d:   0x3033    GOTO 0x033                  ;loop


At the beginning the SP is setup to point to a new location. SP / stack is never used anywhere after this point in calibration program.
So the only use could be from the undocumented instructions LDSPTL and LDSPTH. Also SP points to the memory which is initialized
with static values.

This lets me think LDSPTL/LDSPTL stands for "LoaD from SP Table Low" / "LoaD from SP Table High":
  LDSPTL   =>   A = [SP]
  LDSPTH   =>   A = [SP+1]

Then the above loop would be again some "obfuscation" crypto from PADAUK (XOR 0x55 ... smells like the magic value they love, known from IDE obfuscation).

The result in this case is just 0x11E4 which is then sent out via bitbang to the WRITER to "verify"  :-DD

The loop also serves the purpose to run for several cycles, so WRITER can measure the time it takes and use it for calibration.


JS

EDIT: The loop runs for exact 1040 cycles (including loop init)  :)

Well, 0x55 is a value commonly used in self tests (you'll also see it used as a pattern in memory testers, etc). It has every other bit set, so if there is any interference between adjacent lines it can help detect that. Maybe the program above is one that their test enginers designed to test the ALU? E.g. by making the final result depend on nearly all logic gates or connections in the ALU working correctly?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 22, 2018, 07:15:19 am
SP / stack is never used anywhere after this point in calibration program.
So the only use could be from the undocumented instructions LDSPTL and LDSPTH.

Uhm, don't assume that because the init code initializes the SP it means that he init code uses the stack/SP register. The init code may very well be just initializing it for the user program and stuff.

Also SP points to the memory which is initialized with static values.

It may just be that they had to store some values and instead of touching the upper memory where the MiniC compiler usually places user variables (at least that's what I noticed) they preferred to use the first locations given they will be overwritten by the first push on the stack so "who cares". Maybe for a more "defined" undefined behaviour  :-DD
I mean, unless you fill your ram with vars and you have variables in 0x00, 0x01, ... you'll never end up reading by accident the values that the init code put somewhere, which is coherent with the fact that they're trying to totally hide the init code and its internal working/effects from the user.

This doesn't mean your hypothesis is wrong, IMHO it is very likely that those two instructions act on the stack in that way. But I just wanted to share my thoughts to look at that in a more objective way.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 22, 2018, 07:21:43 am
Could you also add the 13-bit instructions to the documentation on GitHub?

Even better, as soon as I have some time I'll try to find a rule to derive the 13-bit ISA from the 14-bit one. Trust me, after writing by hand dozens of instructions to implement them in the disasm, I can tell there is A LOT of symmetry. I still didn't go in depth but seems it is just something like one bit missing. As soon as I figure that out I'll probably write a tool to do a mass-conversion from the 14-bit docs already up and eventually adjust by hand. Unless someone is already documenting the 13-bit one.

Also, js_12345678_55AA, I had a pull on the docs repo fixing some stuff that is still unfixed after your last commit (a couple of instr swapped IIRC), maybe you want to check that out.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 22, 2018, 12:06:21 pm
Also, js_12345678_55AA, I had a pull on the docs repo fixing some stuff that is still unfixed after your last commit (a couple of instr swapped IIRC), maybe you want to check that out.

Sorry, I did not see the pull request. I merged it now and added you as a project member to github.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 22, 2018, 12:33:20 pm
After reading your comments, resting a bit and looking at the init code again I think I found the real purpose.

It is a CHECKSUM of the code in ROM.

-> the value 0x0055 is the code size (it grows and shrinks when I compile programs with more/less code, verified with IDE)
-> LDSPTL and LDSPTH needs to be 2 different instructions so it can load indirect the low and high byte of the code memory
-> Since code memory can be bigger than 8 bit the pointer to load from needs to be 16bit -> they use the memory where SP is pointing to to store 2 bytes (the pointer to code memory)
-> the XOR, ADD and ROR is just the checksum algorithm they use

LDSPTL: A = LowByte(CodeMem([SP 16bit]))
LDSPTH: A = HighByte(CodeMem([SP 16bit]))

The 16 bit loop counter in init code also serves as pointer into code mem. So it calculates backwards a checksum of all *used* code memory (excluding unused space and special data at end of chip, IDE inserts the real code length in init code).

Only question left is... What are the MSB of LDSPTH when we only have 14 bit stored. Either they read as '1' or as '0'. Experiments with real hardware will show.


Since reading code memory is always a potential thread for chip readout security it would be understandable why this instructions are not in PADAUK user manual.

But with this method we can now store 14 bit tables instead of 8 bit only per instruction word

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 22, 2018, 03:37:14 pm
The checksum thing makes sense only if the programmer is not able to read back the OTP whenever it likes (which I guess is the case). Does that mean you can only verify the code if you disabled "security" or before the calibration phase?

Also worth noting that the PMS150 (non-C version) doesn't have any code like that by looking at its listing (I uploaded it some posts ago). That in fact makes sense, I just checked and the non C version doesn't have the "security" feature you can enable/disable. This mean the programmer can get away calculating the checksum just by reading the OTP which can always be read.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 22, 2018, 04:14:12 pm
There might be an explanation why they do all these checks from another post:

Back in 2006 I was talking to a uC manufacturer in China about their 4 bit uC then costing $0,11 and lower with high volume we were discussing. It could replace $0,40 of logic on our boards so quite interesting with massproduction.
There were some bizar quirks in those things. They were manufactured for one single goal: cheap toys.
The manufacturing process was not as you expect from fabs these days with a result that in your firmware at boottime you had to test the ram since unknown bits would (not could) be dead and you had to make a map so not to use that byte in ram. Also upto 2% of the devices would have problems in the alu or other critical parts. I asked how I could know that the first code would run ok if the ram was not to be trusted. The answer was you could tell from the end product if it worked or not. :-DD
I couldnt believe this but had it b&w in an email.
They probably also sell 100% tested uCs that had no flaws but that was pricewise much less interesting.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 22, 2018, 05:07:54 pm
Actually they even hint to that in their product description. That or low ESD tolerance as that doesnt seem to be selling argument for the cheapest chips.
I guess we will see once someone has programmed a few.

PMC150:
**Very stable performance.
**Using 0.5um OTP process with High EFT proprietary design
**Allow using at high EFT requirement products such as home-appliances and durables etc.
**Operating temperature range: -40°C ~ 85°C

PMS150:
**Valuable price
**Using 0.5um OTP process
**Good for battery or DC power based products but required higher noise immunity
**Not supposed to use in AC RC step-down powered or high EFT requirement applications
**Operating temperature range: -20°C ~ 70°C

PMS150C:
**Very Competitive price
**Using 0.18um OTP process
**Good for battery or DC power based products, such as toys or premiums etc.
**Not supposed to use in AC RC step-down powered or high EFT requirement applications
**Operating temperature range: -20°C ~ 70°C
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 23, 2018, 12:01:06 pm
Hi,

I just got my ICE today... and when you connect it and start debugging you can bring up a disassembly window (no opcodes of course but good to verify our stuff).

I created a new project (name "P2") for PFS154 with the following sample code in "P2.C" (no real purpose, just to check the init code):
Code: [Select]

#include  "extern.h"



void<>FPPA0 (void)
{
  .ADJUST_IC  SYSCLK=IHRC/2    //  SYSCLK=IHRC/2


  while (1){}
}

Then I compiled it and now we got 2 outputs:
 
  - "P2_IDE_LST.txt" is what I got from IDE).

  - "P2_DIS_LST.txt" is from my disassembler using the opcodes we found out


You can see that they hide the "secret" checksum calculation part by inserting a bunch of NOPs (actually ICE really executes NOPs only there). There are also some funny instructions in their output (e.g. when there is an undefined IO)

left from IDE / right from custom disassembler
Code: [Select]
...
00000008     MOV ---- A      /         0x0008:   0x019b    MOV IO(0x1B), A  ;
...
00000033     NOP             /         0x0033:   0x0006    LDSPTL       
00000034     NOP             /         0x0034:   0x0b04    XOR [0x04], A
00000035     NOP             /         0x0035:   0x0007    LDSPTH       
00000036     NOP             /         0x0036:   0x0805    ADD [0x05], A
00000037     NOP             /         0x0037:   0x1584    SL [0x04]   
00000038     NOP             /         0x0038:   0x1685    SLC [0x05]   
00000039     NOP             /         0x0039:   0x1004    ADDC [0x04] 
0000003A     NOP             /         0x003a:   0x1282    DECM [0x02] 
0000003B     NOP             /         0x003b:   0x1083    SUBC [0x03] 
...


Unfortunately when I try to make a program with the undocumented instructions LDSPTL and LDSPTH it compiles fine, but ICE also inserts NOPs there so I can not test their behavior (I need to wait for PFS154 to arrive so I can play with the real IC).

Anyway, our opcode table looks very accurate. :)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 03:21:32 pm
Hi,

I just got my ICE today... and when you connect it and start debugging you can bring up a disassembly window (no opcodes of course but good to verify our stuff).


Is there any way you could determine the type of fpga they are using?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 23, 2018, 03:34:09 pm
Is there any way you could determine the type of fpga they are using?

I will try. Without removing the cover it looks like the surface of the big IC was "chinese polished" (with Dremel  :)).

Will post some pictures later.

JS

EDIT:
USB enumeration shows this:
VID: 0x0797
PID: 0x7002
Device String: "LGS_DEV FX2-HID 0.01"

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 03:50:43 pm
EDIT:
USB enumeration shows this:
VID: 0x0797
PID: 0x7002
Device String: "LGS_DEV FX2-HID 0.01"

The FPPA_IDE.exe has some strings in it refering to:
L.G.S. TECHNOLOGY CO. ,LTD
K.K.K. TECHNOLOGY CO. ,LTD
Kent Lee Developer Studio Version 2014 and an email adress lgs.........@yahoo.com.tw
http://home.kimo.com.tw/lgs............/WEB_EXE_.jpg (http://home.kimo.com.tw/lgs............/WEB_EXE_.jpg)
D:\\KentLee\\Custom\\PDK80\\Source\\Refer\\Test_IC\\Wrt_ROM\\Wrt_ROM.txt

Also the device string you found is included in the exe along with some others:
x6337ec 17 16 IDW-360 FX2-HID
0x633800 17 16 PDK-ICE FX2-HID
0x633814 17 16 LGS-DEV FX2-HID
0x633828 17 16 LGS_DEV FX2-HID

0x6338d4 21 20 Writer : PDK3S-P-002
0x6338ec 30 29 Writer : PDK3S-P-002 (No Cap)
0x63390c 21 20 ICE    : PDK3S-I-002
0x633924 21 20 ICE    : PDK3S-I-003
0x63393c 17 16 SOCKET : EV3-004
0x633950 24 23 ICE    : PDK3S-I-004(*)
0x633968 21 20 ICE    : PDK5S-I-S01
0x633980 21 20 ICE    : PDK5S-I-S02
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 04:03:07 pm
BTW the FX2 chip used has its firmware programmed on the fly (ie when connecting to USB into its onboard RAM), so it should be possible to experiment with it without any risk of bricking it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 23, 2018, 04:09:45 pm
I got my ICE today as well. Here is a high resolution image: https://i.imgur.com/8yef37g.jpg (https://i.imgur.com/8yef37g.jpg)

The FPGA has no markings. It might be possible to capture the JTAG init sequence, if it doesn't store the configuration data inside the FPGA, because looks like there is no external configuration flash memory.

The USB device is a CY7C68013A, with high speed USB (480 Mbps) and an integrated 8051 CPU, that can be booted through USB (there is an interesting project, which implements a communication through such a Cypress chip to a FPGA over USB, FPGALink (http://www.swaton.ukfsn.org/docs/fpgalink/vhdl_paper.pdf)). So this could be a very flexible construction, booting first the firmware of the 8051, then booting the FPGA bitstream, all over USB. But I think it might be easier to develop a new emulator than trying to reverse engineer this. Would be nearly impossible to decode the FPGA bitstream back to the HDL code.

"usb-devices" shows the same as js_12345678_55AA wrote:

Code: [Select]
T:  Bus=01 Lev=01 Prnt=01 Port=01 Cnt=03 Dev#=  9 Spd=480 MxCh= 0                                                                                                                                             
D:  Ver= 2.00 Cls=00(>ifc ) Sub=00 Prot=00 MxPS=64 #Cfgs=  1                                                                                                                                                 
P:  Vendor=0797 ProdID=7002 Rev=80.01                                                                                                                                                                         
S:  Manufacturer=PADAUK                                                                                                                                                                                       
S:  Product=LGS_DEV FX2-HID 0.01                                                                                                                                                                             
C:  #Ifs= 1 Cfg#= 1 Atr=a0 MxPwr=500mA                                                                                                                                                                       
I:  If#= 0 Alt= 0 #EPs= 2 Cls=03(HID  ) Sub=00 Prot=00 Driver=usbhid   
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 04:17:33 pm
I got my ICE today as well. Here is a high resolution image: https://i.imgur.com/8yef37g.jpg (https://i.imgur.com/8yef37g.jpg)

The FPGA has no markings. It might be possible to capture the JTAG init sequence, if it doesn't store the configuration data inside the FPGA, because looks like there is no external configuration flash memory.


Does the FPGA have markings on the bottom? It doesnt look dremeled on the top to me.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 23, 2018, 04:33:56 pm
I got my ICE today as well. Here is a high resolution image: https://i.imgur.com/8yef37g.jpg (https://i.imgur.com/8yef37g.jpg)

The FPGA has no markings. It might be possible to capture the JTAG init sequence, if it doesn't store the configuration data inside the FPGA, because looks like there is no external configuration flash memory.


Does the FPGA have markings on the bottom? It doesnt look dremeled on the top to me.

I just ordered one of these PLCC remover from China. Will report back in 4 weeks when it arrives :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 04:55:10 pm
I just ordered one of these PLCC remover from China. Will report back in 4 weeks when it arrives :)

I try to anticipate these things and ordered my 3.5$ FX2 dev board a week ago  ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: mikeselectricstuff on November 23, 2018, 05:55:27 pm
Hi,

I just got my ICE today... and when you connect it and start debugging you can bring up a disassembly window (no opcodes of course but good to verify our stuff).


Is there any way you could determine the type of fpga they are using?
Could be a CPLD - plenty of PLC44 options showing on Digikey for that package. If there is 5V anywhere that would narrow it down a lot.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 06:16:36 pm
Could be a CPLD - plenty of PLC44 options showing on Digikey for that package. If there is 5V anywhere that would narrow it down a lot.

I'm kind of hoping for a XC9572XL. It could very well be a cpld because the newest version (5S
-I-S02B dated 2017/7/24) of the ice also uses a socketed plcc44.

On second thought a CPLD probably does not have enough memory on board to emulate a full chip so must be something else.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gdelazzari on November 23, 2018, 06:46:12 pm
I'm reporting a conversation between me and js_12345678_55AA regarding planning of what to do next (and how) if anyone wants to share its thoughts. Not sure why I didn't directly post here in the forum thread, sorry for that  :-//

The things of most interest are probably the assembler and the syntax

Quote
Hi,

>Hi, do you have any plans to upload your disassembler (and eventually assembler if you have one) to the GitHub organization?

Sure I will do (I just want to structure it a bit more, will take 1-2 days)


>I also have tools in a preliminary state working with the 13-bit and 14-bit ISAs, which unfortunately is duplicate work but I wanted to disasm some listings so I proceeded anyway in implementing them, but that was not a lot of work so it's not a problem for me to trash everything if we want to keep your infrastructure.

All of the code I did is also just for experimentation. Most likely it will be replaced by better implementations later. So no need to keep / stick to something from me right now.


>Also I think we should define a bit how we want to proceed with the assembler.

I did not start with an assembler implementation. Maybe this is something you/somebody else want to try?
I'm already busy reversing stuff and find out how things are connected.
Today my WRITER and SIMULATOR arrived. So now I can start to work with real hardware :-)


>Some stuff to be discussed may be:
>- syntax quirks (how to represent various kind of values/addresses), asm directives, macros, defines, includes, etc...

I did not really investigated on this. I just used a syntax which I thought was good enough for first tests.
Mainly I used the syntax PADAUK used in their manuals. Just to distinguish between RAM / ROM / IO we would need to invent something. Note: The "." syntax is mainly used to represent a special bit (8051 assembly). "[ ]" are used for normal memory access. "WORD PTR" is usually used for 16 bit address references, ... I think we should adapt already known schemes so it easier for others to understand

Creating a document defining the syntax of the assembler would be a good starting point.

I think during implementation of assembler some changes will be required. Since the disassembler is fairly easy to adapt I consider it to follow any syntax changes the assembler creator might need to do.


>- whether to deviate from PADAUK's ASM syntax and implement something of our own, or whether to implement their same syntax for compatibility; or even both at the same time (i.e. a flag to choose the syntax)

One syntax please :-). As close as possible to PADAUK syntax with just some extensions for direct memory/io access.


>- what binary format we want to use across the open source toolchain, i.e. just the raw ROM content on a .bin file, or keeping their PDK format for compatibility with their OTP Writer, or have our own format, or a mix of these three things, or whatever :)

I think we should use the PDK format. The creation for a "liberated" WRITER seems to be the most difficult part which most likely will take the longest time.


>- if it makes sense to keep the ISA description open enough so that it can be imported by someone that wants to implement for instance an SDCC backend or a radare2 plugin to disasm, etc... or just keep it simple and hard coded in the tools

The ISA is so small and simple, everyone can adapt and implement it for a disasm within a few hours. So I think there is no need to be generic here.


>Also, regarding an hypothetical PC simulator (not real time, maybe cycle accurate, or even not) for debugging only:

Why "hypothetical PC simulator"? I finished this task already  8)


>- how that would be presented to the user, i.e.
>- a GUI? With what features? I/O interaction?
>- some kind of simulation you launch and outputs a waveform file in some standard format for inspection later (and that can also accept an input waveform file or some kind of description of what to do with the inputs - i.e. after 0.1s set PA.3 high etc...)
>- a command line tool like GDB where you can single step, inspect memory and regs, run, pause, etc...
>- a combination of some of the things above
>- ...

I was having a look at a 8051 emulator which uses ncurses ( https://github.com/jarikomppa/emu8051 ). This simulator I plan to repurpose for the front end.


>- we'll need our own init code if we want to create a full toolchain you can use from start to finish without touching PADAUK's tools, what should be done in that regard? Should we replicate PADAUK's code (eventually improving it) or do something else? Maybe have different init code options i.e. if you don't need precise clock speeds you can free up space by not having the calibration code, or you can chose to have it, you can have the ROM checksum or not, etc...

The init code is tied to the WRITER which I think we should stay compatible with (see comment above).
Usually this kind of things (init code) is implemented in include (.INC) files which the developer gets automatically in his project when he starts a new project (e.g. from a empty project template).
Then it up to the developer to modify / delete stuff from init code or use different/optimized implementations.


>- least important thing in this message but cool: a library of pre-made routines for stuff like SPI, UART, etc... could be made and optimized by the community. Like a collection of include files "spi.inc" "uart.inc" you can just bring in and use would be pretty cool

Personally I prefer simple sample projects with code snippets I can just cut and paste to my project. I don't like big libraries (like Arduino or STM32). Especially when every byte counts.


>The STM32 emulator you're working on is also vital in the toolchain I think, so keep that up. I started to play around with some methods of efficiently emulating the code on ARM Thumb by checking what assembly GCC generates for various approaches, and it seems like writing the time critical parts in assembly may be the easiest route... GCC insists on keeping the PC/ACC/ecc in RAM but having 12 general purpose registers I think the best thing is to assign the ACC, PC, SP, etc... to a couple of regs and avoid all the LDRs that just slow things down. Of course I may be wrong and there may be a way to write the C code in such a way that GCC does this by itself, but I still didn't find a way. I thought we could map every PADAUK's cycle to 8 cortex cycles with a CPU clock of 64MHz which sounds a reasonable choice given there's the ultracheap STM32F103C8T6 everywhere on eBay, Aliexpress, etc... that fits that frequency, staying in an 8 cycle frame might be viable if most of the stuff is in registers since most instructions take 1 cycle only. Did you make any progress regarding emulation on STM32?

After implementing the FLAG solver for AC and OV i recognized emulation will be quite complex.
Also keep in mind that you need to emulate the CLOCK, IO, PWM, INTERRUPTS, TIMER, WATCHDOG, ...
So I don't think a near real time emulation on STM32 will be possible.

But why not using FPGA? Simple ones are also very cheap. And one guy here in forum already said he would be able to create a FPGA version.


>Let me know what you think about my points and how we should proceed. If we can coordinate at least a bit the work that should be done (and how it should be done) I can start working on some tools.

Creating the assembler would be nice.
I really would love to have an assembler as soon as possible so I can automate tests for the simulator :-)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 23, 2018, 08:04:05 pm
Does the FPGA have markings on the bottom? It doesnt look dremeled on the top to me.

Here comes the money shot:

Picture shows the ICE main IC (PLCC 44) from bottom.

Based on the top shape / edge / dot / corner  and the "SCD" marking on the bottom it most probably is a Xilinix.

Shape matches exact this drawing: https://japan.xilinx.com/support/documentation/package_specs/pc44.pdf  Most other PLCC44 FPGA/CLPD have marks on top / 2 edges / no dot in middle / ...



Happy hunting!

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 23, 2018, 08:32:03 pm
Reverse engineering the writer firmware might be a good idea, but to be sure maybe would be good to record a programming sequence as well.

I did some tests. I have only some free PMC884 samples at the moment which Padauk sent me. I also bought some PMS150C chips from lcsc.com, as recommended by Padauk, but needs some time until I get them.

First I programmed a blinky program, with all 8 FFPAs and different output frequencies. This is the main file (full project is attached) :

Code: [Select]
// define pin names
Out0 BIT PB.0;
Out1 BIT PB.1;
Out2 BIT PB.2;
Out3 BIT PB.3;
Out4 BIT PB.4;
Out5 BIT PB.5;
Out6 BIT PB.6;
Out7 BIT PB.7;

// FPPA0 is started first
void FPPA0 (void)
{
.ADJUST_IC SYSCLK=IHRC/2, IHRC=16MHz, VDD=5V, Bandgap=On;

// set pins to output
$ Out0 High, Out;
$ Out1 High, Out;
$ Out2 High, Out;
$ Out3 High, Out;
$ Out4 High, Out;
$ Out5 High, Out;
$ Out6 High, Out;
$ Out7 High, Out;

// see datasheet "pmode": FPPA duty cycle, 1/8 for all 8 FPPAs
pmode 31;

// enable all FPPAs
fppen = 0xFF;

// generate test output
while (1) {
Out0 = 0;
.delay 1;
Out0 = 1;
.delay 1;
}
}

void FPPA1 (void)
{
// generate test output
while (1) {
Out1 = 0;
.delay 10;
Out1 = 1;
.delay 10;
}
}

void FPPA2 (void)
{
// generate test output
while (1) {
Out2 = 0;
.delay 100;
Out2 = 1;
.delay 100;
}
}

void FPPA3 (void)
{
// generate test output
while (1) {
Out3 = 0;
.delay 1000;
Out3 = 1;
.delay 1000;
}
}

void FPPA4 (void)
{
// generate test output
while (1) {
Out4 = 0;
.delay 10000;
Out4 = 1;
.delay 10000;
}
}

void FPPA5 (void)
{
// generate test output
while (1) {
Out5 = 0;
.delay 100000;
Out5 = 1;
.delay 100000;
}
}

void FPPA6 (void)
{
// generate test output
while (1) {
Out6 = 0;
.delay 1000000;
Out6 = 1;
.delay 1000000;
}
}

void FPPA7 (void)
{
// generate test output
while (1) {
Out7 = 0;
.delay 10000000;
Out7 = 1;
.delay 10000000;
}
}

/*
void Interrupt (void)
{
pushaf;

if (Intrq.T16)
{ // T16 Trig
// User can add code
Intrq.T16 = 0;
//...
}

popaf;
}

*/

I measured the following frequencies (AVDD needs to be connected as well, otherwise looks like the internal oscillator doesn't run) :

Code: [Select]
PB0: 203 kHz
PB1: 44 kHz
PB2: 5 kHz
PB3: 508 Hz
PB4: 50.8 Hz
PB5: 5.08 Hz
PB6: 0.5 Hz
PB7: 0.05 Hz

Nice about the PMC884 is that you can select the duty cycle scheme, e.g. if you want to run FFPA0 more than the other FFPAs. So this was just a first test to see if everything works.

Then I tried to measure the programming signals (as David already noted in his video, you can program the OTP chip as often as you want, if it is the same bitstream). But connecting GND of the scope to the GND pin of the microcontroller was not a good idea, because the programmer tests all pins for shorts and then doesn't start the programming sequence. But here is a nice GND point near the jumpers at the back:

(https://i.imgur.com/dA7DO93.jpg)

Then I measured some pins. In David's video it was difficult or impossible to see the timescale. Here is an example for pin 3, this time with proper time scale, for the whole programming cycle:

(https://i.imgur.com/XQ2UNWY.png)

This is a data pin. Pin 19 is a clock pin. When I zoom in, it looks like this:

(https://i.imgur.com/J5Li93k.png)

Looks like about 1 us is the shortest signal length. Might be good to sample it with 10 MHz for higher resolution.

I don't know how many signals I need to scan in parallel, 2 might be enough with multiple passes, but maybe 4 would be better and easier to analyze later. If I use an 8 bit ADC, this would mean a data rate of 320 Mbits/s. Might be possible with high speed USB to transfer it in realtime on a PC. As you can see in the first scope image, the whole programming cycle needs about 800 ms (the spikes before and after are the detection of the programmer if there is a chip, which does it all the time). So a full sample with 4 channels would need only 32 MB. This could be even done with a BeagleBone and its PRUs, a simple external board with 4 ADCs and input stages for dividing the input voltage, and then recording it to memory.

But I don't have much time at the moment to build the board and program the Beagle Bone. Is there already such a thing I can buy, which records 4 channels with 8 bit at 10 MHz for 1 second?

PS: Anyone who wants to swap some PMS150C (or other Padauk) chips for PMC884? I have 100 x PMC884. Here (http://www.frank-buss.de/tmp/pmc884.pdf) is the datasheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 09:00:43 pm
Does the FPGA have markings on the bottom? It doesnt look dremeled on the top to me.

Here comes the money shot:

Picture shows the ICE main IC (PLCC 44) from bottom.

Based on the top shape / edge / dot / corner  and the "SCD" marking on the bottom it most probably is a Xilinix.

Shape matches exact this drawing: https://japan.xilinx.com/support/documentation/package_specs/pc44.pdf  Most other PLCC44 FPGA/CLPD have marks on top / 2 edges / no dot in middle / ...



Happy hunting!

JS

Thank you very much!

judging from lcsc pictures xilinx chips dont have bottom markings.
Also I think that padauk might have put their own markings on the bottom because it would match their package marking scheme

However I have the strong feeling this is neither a fpga nor a cpld but an 8051, because the beginning of the deobfuscated pdk files looks like this, which kind of looks like a jump table:

X0000:   add   a,r2
X0001:   xrl   rb0r2,a
   anl   a,r6
   xrl   a,r4
   jnz   X005e
   jnc   X005b
   jnc   X006a
   jnc   X0061
X000d:   jnc   X0062
   jnc   X0020
   acall   X0357
   jnc   X0064
   jnc   X0076
X0017:   jnc   X006d
   jnc   X005e
   jnc   X0060
   jnc   X0038
   acall   X0357
   jnc   X0075
   jnc   X0084
   jnc   X007b
   jnc   X0074
   jnc   X0070
   jnc   X005e
X002d:   jnc   X0057
   acall   X0357
   jnc   X0085

the markings in the circles in the corners look similar to those of stc 8051 chips on lcsc (up to 80 Mhz apperantly). Maybe they do software emulation on an 8051?  :-//

Is that feasible? Are the files in USB_Driver/USB/ICE* really 8051ish code?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on November 23, 2018, 09:17:05 pm
Is that feasible? Are the files in USB_Driver/USB/ICE* really 8051ish code?

The 8051 code might be for the Cypress USB microcontroller, which can load firmware over USB for itself as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 23, 2018, 09:24:52 pm
There are *.hid files for that which fill the complete 8 to 16kb for the fx2

But its really hard to say, the first part of the *pdk (unobfuscated) could very well also be lets say I/O mappings of an FPGA.

However its very hard to find any in an plcc44, cpld dont really fit the profile because they dont have sufficient memory to emulate ram/rom of the micro, and that basically leaves other microcontrollers.

Weird.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: westfw on November 23, 2018, 09:49:58 pm
I'm a bit surprised that I don't see any voltage switching circuits between the PLCC and the connector that leads to the chip?   That would sort-of imply that the chip has some analog capability rather than being a digital FPGA?
(oh wait - is this "ICE Only" box with no programmer?  If so, never mind...)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 24, 2018, 09:09:41 am
I'm reporting a conversation between me and js_12345678_55AA regarding planning of what to do next (and how) if anyone wants to share its thoughts. Not sure why I didn't directly post here in the forum thread, sorry for that  :-//

The things of most interest are probably the assembler and the syntax

Quote
Hi,

>Hi, do you have any plans to upload your disassembler (and eventually assembler if you have one) to the GitHub organization?

Sure I will do (I just want to structure it a bit more, will take 1-2 days)


>I also have tools in a preliminary state working with the 13-bit and 14-bit ISAs, which unfortunately is duplicate work but I wanted to disasm some listings so I proceeded anyway in implementing them, but that was not a lot of work so it's not a problem for me to trash everything if we want to keep your infrastructure.

All of the code I did is also just for experimentation. Most likely it will be replaced by better implementations later. So no need to keep / stick to something from me right now.


>Also I think we should define a bit how we want to proceed with the assembler.

I did not start with an assembler implementation. Maybe this is something you/somebody else want to try?
I'm already busy reversing stuff and find out how things are connected.
Today my WRITER and SIMULATOR arrived. So now I can start to work with real hardware :-)


>Some stuff to be discussed may be:
>- syntax quirks (how to represent various kind of values/addresses), asm directives, macros, defines, includes, etc...

I did not really investigated on this. I just used a syntax which I thought was good enough for first tests.
Mainly I used the syntax PADAUK used in their manuals. Just to distinguish between RAM / ROM / IO we would need to invent something. Note: The "." syntax is mainly used to represent a special bit (8051 assembly). "[ ]" are used for normal memory access. "WORD PTR" is usually used for 16 bit address references, ... I think we should adapt already known schemes so it easier for others to understand

Creating a document defining the syntax of the assembler would be a good starting point.

I think during implementation of assembler some changes will be required. Since the disassembler is fairly easy to adapt I consider it to follow any syntax changes the assembler creator might need to do.


>- whether to deviate from PADAUK's ASM syntax and implement something of our own, or whether to implement their same syntax for compatibility; or even both at the same time (i.e. a flag to choose the syntax)

One syntax please :-). As close as possible to PADAUK syntax with just some extensions for direct memory/io access.


>- what binary format we want to use across the open source toolchain, i.e. just the raw ROM content on a .bin file, or keeping their PDK format for compatibility with their OTP Writer, or have our own format, or a mix of these three things, or whatever :)

I think we should use the PDK format. The creation for a "liberated" WRITER seems to be the most difficult part which most likely will take the longest time.


>- if it makes sense to keep the ISA description open enough so that it can be imported by someone that wants to implement for instance an SDCC backend or a radare2 plugin to disasm, etc... or just keep it simple and hard coded in the tools

The ISA is so small and simple, everyone can adapt and implement it for a disasm within a few hours. So I think there is no need to be generic here.


>Also, regarding an hypothetical PC simulator (not real time, maybe cycle accurate, or even not) for debugging only:

Why "hypothetical PC simulator"? I finished this task already  8)


>- how that would be presented to the user, i.e.
>- a GUI? With what features? I/O interaction?
>- some kind of simulation you launch and outputs a waveform file in some standard format for inspection later (and that can also accept an input waveform file or some kind of description of what to do with the inputs - i.e. after 0.1s set PA.3 high etc...)
>- a command line tool like GDB where you can single step, inspect memory and regs, run, pause, etc...
>- a combination of some of the things above
>- ...

I was having a look at a 8051 emulator which uses ncurses ( https://github.com/jarikomppa/emu8051 ). This simulator I plan to repurpose for the front end.


>- we'll need our own init code if we want to create a full toolchain you can use from start to finish without touching PADAUK's tools, what should be done in that regard? Should we replicate PADAUK's code (eventually improving it) or do something else? Maybe have different init code options i.e. if you don't need precise clock speeds you can free up space by not having the calibration code, or you can chose to have it, you can have the ROM checksum or not, etc...

The init code is tied to the WRITER which I think we should stay compatible with (see comment above).
Usually this kind of things (init code) is implemented in include (.INC) files which the developer gets automatically in his project when he starts a new project (e.g. from a empty project template).
Then it up to the developer to modify / delete stuff from init code or use different/optimized implementations.

[…]

>Let me know what you think about my points and how we should proceed. If we can coordinate at least a bit the work that should be done (and how it should be done) I can start working on some tools.

Creating the assembler would be nice.
I really would love to have an assembler as soon as possible so I can automate tests for the simulator :-)


My plans so far:

Things I will help with (I know someone who might want to do part of this):

What I'd like to see but don't want to do myself:

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 24, 2018, 10:42:26 am
I have a simulator implemented and somewhat working (have not tested all
instructions yet), and trying to run the startup code generated by the
assembler exposed a "weirdness" I had not noticed before:

The assembler insists that you put these startup macros in, so I used the
samples found in Demo/Dummy/Dummy.asm :

------------------- Cut here -------------
.CHIP PMS150
//{{PADAUK_CODE_OPTION
        .Code_Option    Under_20mS_VDD_Ok       No
        .Code_Option    LVR             2.5V
        .Code_Option    Security        Disable// Security Disable
//}}PADAUK_CODE_OPTION
.WRITER O_S
        .ADJUST_IC      SYSCLK=IHRC/8, IHRC=16MHz, VDD=5V;
------------------- Cut here -------------

Here is a disassembly of what it generates:

0000: 1700   MOV     A,0x00
0001: 0085   MOV     IO.0x05,A
0002: 0FE4   SET1    IO.0x04.7   // B7 documented as "reserved"
0003: 1700   MOV     A,0x00
0004: 0082   MOV     IO.0x02,A
0005: 1700   MOV     A,0x00
0006: 008B   MOV     IO.0x0B,A
0007: 173C   MOV     A,0x3C
0008: 0083   MOV     IO.0x03,A
0009: 1FFE   CALL    03FE       // ?? This is the problem ??
000A: 12FF   CEQSN   A,0xFF
000B: 181C   GOTO    001C
000C: 0FD1   SET1    IO.0x11.6
000D: 0981   CLEAR   MEM.0x01
000E: 1709   MOV     A,0x09
000F: 05C0   MOV     MEM.0x00,A
0010: 0D90   T1SN    IO.0x10.4
0011: 1810   GOTO    0010
0012: 0FD0   SET1    IO.0x10.6
0013: 0013   DZSN    A
0014: 1813   GOTO    0013
0015: 08C0   DZSN    MEM.0x00
0016: 1813   GOTO    0013
0017: 0ED0   SET0    IO.0x10.6
0018: 0901   INC     MEM.0x01
0019: 07C1   MOV     A,MEM.0x01
001A: 008B   MOV     IO.0x0B,A
001B: 180E   GOTO    000E
 // .. user code goes here
03F8: 0000   NOP     
03F9: 0000   NOP     
03FA: 0000   NOP     
03FB: 0000   NOP     
03FC: 0000   NOP     
03FD: 0000   NOP     
03FE: 1FFF   CALL    03FF
03FF: 1F9D   CALL    039D

As you can see, it generates a CALL to address 0x3FE which contains all
ones which is the default value for unused locations, and happens to
translate to "CALL 03FF".

Prior to doing this, they set Bit7 of IO.4 which is the interrupt enable
register, and Bit7 is documented as "reserved".

Following the CALL 03FE they test the accumulator value for 0xFF, and
going in to the call, it is clearly 0x3C - so they expect that this CALL
can modify the accumulator.

I'm wondering if setting IO.4.7 is mapping some special code, perhaps
"RET immediate" into the reserved area in order to retrieve some chip
dependant value, but I have no way to test this. It is also possible
that the progammer automatically programs some calibration value into
this location, however that leads to two questions:

1) What does the ICE do in this case?
2) The obtained value is only used to either 1) continue the startup
   code, or 2) jump directly to the user code bypassing the remainder
   of the startup code, why would the writer be making this decision
   For that matter why would anything not under user control be
   doing this?, it does not appear to be a calibration value as it is
   lost 4 instructions later having not been used.

Could someone with the ICE look into this and see what is happening?

Thanks,
Dave
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 24, 2018, 11:53:05 am
Hello DDunfield,

I posted a complete commented disassembly of the init code some posts back in this thread.

If you look in the .INC file of a regular project you can see more IO definitions (e.g. IO 0x0b is called "IHRCR"  which is the InternalHighspeedRC-Register").

IO 0x0B (IHRCR) will hold a "tuning" value to tune the internal high speed oscillator.


The complete init code is used to set a specific value and go up and down commanded by WRITER so it can measure and tuning the oscillator.

At first write WRITER places a "RET 0xFF" at last position of ROM-1 (0x3FE in your case).

So when WRITER starts the IC init code is executed. Then it uses bit bang protocol on PA to get data in (+/-1 of current IHRCR value) and out (checksum of code) and can measure the timing of the process.
When WRITER is done it overwrites the "RET 0xFF" with "RET 0xXY" so all later starts of the IC will not execute the init code at all. Just the defined IHRC value is written to IHRCR.

The overwriting of OTP is possible only when you change '1' bits to '0' so you can change value 0xFF to anything (but not the other way around, 0x00 can not be changed to anything anymore).
The OTP writing just can change '1' bits to '0' permanently.

Have fun,

JS.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 25, 2018, 01:56:32 pm
Here is some C++ code that will decode and encode the MCU firmware contained within a PDK file. This operates in-place in memory. Derived from code posted by js_12345678_55AA.

The encoder/decoder...
Code: [Select]
void xcode_pdk_data(TPDKinfo &info, bool encode)
{
    if (info.length & 31) return; // Must be a multiple of 32 words

    uint16_t const x0 = 0x55AA;
    CKey key(info.key);
    uint16_t x1 = key[3] ^ key[14];
    uint16_t x2 = key[7] ^ key[15];
    if ((info.version >= 0x15) && (info.version <= 0x17))
        x1 ^= 0x1234, x2 ^= 0x5678;
    uint16_t t1 = 0, t2 = 0;
    unsigned ki = 0, n = 0;
    uint16_t *d = info.data;

    while (n < info.length) {
        for (unsigned j = 0; j < 4; ++j) {
            if (encode) {
                t1 = *d++ = (*d - key[ki += x1])     ;    key[ n] ^= t1;
                t2 = *d++ = (*d ^ key[ki += t1]) - x2;    key[x2] ^= x1;
                x1 = *d++ = (*d - key[ki ^= t2])     ;    key[x2] ^= x0;
                x2 = *d++ = (*d ^ key[ki = kx(ki, x1)]) + t1;
                t1 = *d++ = (*d ^ key[ki += x2])     ;    key[x1] += x2;
                t2 = *d++ = (*d ^ key[ki ^= t1]) ^ x2;    key[t2] ^= t1;
                x1 = *d++ = (*d - key[ki ^= t2])     ;    key[t1] += t2;
                x2 = *d++ = (*d ^ key[ki += x1]) - t1;
            } else {
                *d++ = ((t1 = *d)     ) + key[ki += x1];   key[ n] ^= t1;
                *d++ = ((t2 = *d) + x2) ^ key[ki += t1];   key[x2] ^= x1;
                *d++ = ((x1 = *d)     ) + key[ki ^= t2];   key[x2] ^= x0;
                *d++ = ((x2 = *d) - t1) ^ key[ki = kx(ki, x1)];
                *d++ = ((t1 = *d)     ) ^ key[ki += x2];   key[x1] += x2;
                *d++ = ((t2 = *d) ^ x2) ^ key[ki ^= t1];   key[t2] ^= t1;
                *d++ = ((x1 = *d)     ) + key[ki ^= t2];   key[t1] += t2;
                *d++ = ((x2 = *d) + t1) ^ key[ki += x1];
            }
            key[1] ^= key[15]; key[2] ^= t1;
            key[3] ^= key[14]; key[4] += t2;
            key[5] ^= key[13]; key[6] += x2;
            key[8] -= x1;
            ki += j;
        }
        n += 32;
    }
}

The other stuff...
Code: [Select]
struct TPDKinfo
{
    unsigned version;
    unsigned length;
    uint16_t *key;
    uint16_t *data;
};

class CKey
{
private:
    uint16_t k[16];
public:
    CKey(uint16_t *_k) { memcpy(k, _k, sizeof(k)); }
    inline uint16_t & operator [] (unsigned const i) { return k[i & 15]; }
};

static inline unsigned kx(unsigned const k, unsigned const i) { return ((k & 0xFFFF) + (i & 0xFFFF)) >> 1; }


/* xcode_pdk_data() goes here */


int get_pdk_info(uint8_t *bd, unsigned len, TPDKinfo &info)
{
    // Note: this will only work on little endian CPUs due to the use of
    //          uint16_t and uint32_t reinterpret casts

    memset(&info, 0, sizeof(info));

    if (len < 256) return -1; // Header too short

    uint16_t *wd = reinterpret_cast<uint16_t *>(bd); // Word (16 bit) data pointer
    uint32_t *ld = reinterpret_cast<uint32_t *>(bd); // Long (32 bit) data pointer

    uint32_t const version = ld[4 >> 1];
    info.version = version;

    uint32_t const datalen = ld[16 >> 1];
    if (datalen & 31) return -2; // Data size is not a multiple of 32
    info.length = datalen;

    uint32_t const extrahdr = wd[0x13] + wd[0x14] + wd[0x16] + wd[0x68] + (version > 0x1C ? wd[0x24] >> 8 : 0);
    if (extrahdr & 1) return -3; // Data is not word aligned

    uint32_t const hdrlen = 256 + extrahdr;
    if (len < hdrlen + (datalen << 1)) return -4; // Not enough data

    info.key = wd + 0x70;
    info.data = reinterpret_cast<uint16_t *>(bd + hdrlen);

    return 0;
}

void decode_fw(uint16_t *d, unsigned len)
{
    uint16_t const o[8] = { 0xAFCD, 0x0055, 0xAA23, 0x0055, 0x3759, 0x0055, 0xAA23, 0x0055 };
    unsigned j = len << 3;
    unsigned i = 0;
    do *d++ ^= o[i & 7] ^ i++ ^ (j -= 8); while (j);
}

int main()
{
    // Read a PDK file into memory
    FILE *f;
    errno_t e = fopen_s(&f, "test.pdk", "rb");
    if (e) return -1;
    uint8_t x[9000];
    unsigned const l = fread(x, 1, sizeof(x), f);
    fclose(f);
    if (!l) return -2;

    // Get info from the header
    TPDKinfo info;
    if (get_pdk_info(x, l, info)) return -3;
    printf("PDK version: %i\nPDK data size: %i words\n", info.version, info.length);

    // Decode it
    xcode_pdk_data(info);

    // Write the decoded file
    e = fopen_s(&f, "test_decode.bin", "wb");
    if (e) return -4;
    fwrite(x, 1, l, f);
    fclose(f);

    // Encode it
    xcode_pdk_data(info, true);

    // Write the encoded file
    e = fopen_s(&f, "test_encode.bin", "wb");
    if (e) return -4;
    fwrite(x, 1, l, f);
    fclose(f);

    return 0;
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 25, 2018, 04:42:10 pm
16 bit instruction set encoding used by PMS234

The encoding allows for addressing of up to 64 byte IO, 512 byte RAM and 8192 word program.

EDIT: Added a few instructions that I missed (skipped a page in the manual)

Code: [Select]
0000_0000_0000_0000  nop
0000_0000_0001_0000  addc     a
0000_0000_0001_0001  subc     a
0000_0000_0001_0010  izsn     a
0000_0000_0001_0011  dzsn     a
0000_0000_0001_0111  pcadd    a
0000_0000_0001_1000  not      a
0000_0000_0001_1001  neg      a
0000_0000_0001_1010  sr       a
0000_0000_0001_1011  sl       a
0000_0000_0001_1100  src      a
0000_0000_0001_1101  slc      a
0000_0000_0001_1110  swap     a
0000_0000_0001_1111  delay    a
0000_0000_0011_0000  wdreset
0000_0000_0011_0010  pushaf
0000_0000_0011_0011  popaf
0000_0000_0011_0101  reset
0000_0000_0011_0110  stopsys
0000_0000_0011_0111  stopexe
0000_0000_0011_1000  engint
0000_0000_0011_1001  disgint
0000_0000_0011_1010  ret
0000_0000_0011_1011  reti
0000_0000_10pp_pppp  mov      IO,a
0000_0000_11pp_pppp  mov      a,IO
0000_0001_kkkk_kkkk  cneqsn   a,I
0000_001w_wwww_www0  stt16    word
0000_001w_wwww_www1  ldt16    word
0000_100w_wwww_www0  idxm     index,a
0000_100w_wwww_www1  idxm     a,index
0000_101w_wwww_www0  ldtabl   word
0000_101w_wwww_www1  ldtabh   word
0000_1110_kkkk_kkkk  delay    I
0000_1111_kkkk_kkkk  ret      I
0001_0000_00pp_pppp  xor      IO,a
0001_0000_01pp_pppp  xor      a,IO
0001_011m_mmmm_mmmm  cneqsn   a,M
0001_1000_kkkk_kkkk  add      a,I
0001_1001_kkkk_kkkk  sub      a,I
0001_1010_kkkk_kkkk  ceqsn    a,I
0001_1011_kkkk_kkkk  comp     a,I
0001_1100_kkkk_kkkk  and      a,I
0001_1101_kkkk_kkkk  or       a,I
0001_1110_kkkk_kkkk  xor      a,I
0001_1111_kkkk_kkkk  mov      a,I
0010_000b_bbpp_pppp  t0sn     IO.n
0010_001b_bbpp_pppp  t1sn     IO.n
0010_010b_bbpp_pppp  set0     IO.n
0010_011b_bbpp_pppp  set1     IO.n
0010_100b_bbpp_pppp  tog      IO.n
0010_101b_bbpp_pppp  wait0    IO.n
0010_110b_bbpp_pppp  wait1    IO.n
0010_111b_bbpp_pppp  swapc    IO.n
0011_000m_mmmm_mmmm  nmov     M,a
0011_001m_mmmm_mmmm  nmov     a,M
0011_010m_mmmm_mmmm  nadd     M,a
0011_011m_mmmm_mmmm  nadd     a,M
0011_100m_mmmm_mmmm  ceqsn    M,a
0011_101m_mmmm_mmmm  ceqsn    a,M
0011_110m_mmmm_mmmm  comp     M,a
0011_111m_mmmm_mmmm  comp     a,M
0100_000m_mmmm_mmmm  add      M,a
0100_001m_mmmm_mmmm  add      a,M
0100_011m_mmmm_mmmm  sub      a,M
0100_100m_mmmm_mmmm  addc     M,a
0100_101m_mmmm_mmmm  addc     a,M
0100_010m_mmmm_mmmm  sub      M,a
0100_111m_mmmm_mmmm  subc     a,M
0100_110m_mmmm_mmmm  subc     M,a
0101_000m_mmmm_mmmm  and      M,a
0101_001m_mmmm_mmmm  and      a,M
0101_010m_mmmm_mmmm  or       M,a
0101_011m_mmmm_mmmm  or       a,M
0101_100m_mmmm_mmmm  xor      M,a
0101_101m_mmmm_mmmm  xor      a,M
0101_110m_mmmm_mmmm  mov      M,a
0101_111m_mmmm_mmmm  mov      a,M
0110_000m_mmmm_mmmm  addc     M
0110_001m_mmmm_mmmm  subc     M
0110_010m_mmmm_mmmm  izsn     M
0110_011m_mmmm_mmmm  dzsn     M
0110_100m_mmmm_mmmm  inc      M
0110_101m_mmmm_mmmm  dec      M
0110_110m_mmmm_mmmm  clear    M
0110_111m_mmmm_mmmm  xch      M
0111_000m_mmmm_mmmm  not      M
0111_001m_mmmm_mmmm  neg      M
0111_010m_mmmm_mmmm  sr       M
0111_011m_mmmm_mmmm  sl       M
0111_100m_mmmm_mmmm  src      M
0111_101m_mmmm_mmmm  slc      M
0111_110m_mmmm_mmmm  swap     M
0111_111m_mmmm_mmmm  delay    M
1000_bbbm_mmmm_mmmm  t0sn     M.n
1001_bbbm_mmmm_mmmm  t1sn     M.n
1010_bbbm_mmmm_mmmm  set0     M.n
1011_bbbm_mmmm_mmmm  set1     M.n
110a_aaaa_aaaa_aaaa  goto     label
111a_aaaa_aaaa_aaaa  call     label
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 25, 2018, 05:02:00 pm
16 bit instruction set encoding used by PMS234

...

Code: [Select]
0000_0000_0001_1111  delay    a
...

Maybe delay instruction is also available in 14 bit ? There is an empty space in opcode list there...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 25, 2018, 06:05:56 pm
PMS234 startup code

Code: [Select]
000  C002  goto    0x002
001  C049  goto    0x049
002  1F00  mov     a,0x00
003  0082  mov     SP,a
004  1F00  mov     a,0x00
005  008B  mov     IHRCR,a
006  EFFD  call    0x3FD
007  00B8  mov     A_IHRC,a
008  1F3C  mov     a,0x3C
009  0083  mov     CLKCMD,a
00A  1F0F  mov     a,0x0F
00B  5C01  mov     M001,a
00C  1FFE  mov     a,0xFE
00D  5C00  mov     M000,a
00E  0A00  ldtabl  M000
00F  1AFF  ceqsn   a,0xFF
010  C040  goto    0x040
011  2791  set1    PAC.6
012  6C01  clear   M001
013  1F20  mov     a,0x20
014  5C00  mov     M000,a
015  2D10  wait1   PA.4
016  2790  set1    PA.6
017  001F  delay   a
018  6600  dzsn    M000
019  C017  goto    0x017
01A  2590  set0    PA.6
01B  2210  t1sn    PA.0
01C  C03C  goto    0x03C
01D  1FA4  mov     a,0xA4
01E  00A0  mov     ADCC,a
01F  1F84  mov     a,0x84
020  00A1  mov     ADCM,a
021  1F80  mov     a,0x80
022  5C00  mov     M000,a
023  5E00  mov     a,M000
024  00B9  mov     BGTR,a
025  27A0  set1    ADCC.6
026  2DA0  wait1   ADCC.6
027  27A0  set1    ADCC.6
028  2DA0  wait1   ADCC.6
029  00E2  mov     a,ADCRH
02A  5C01  mov     M001,a
02B  00E3  mov     a,ADCRL
02C  2CD0  wait1   PA.3
02D  001B  sl      a
02E  7A01  slc     M001
02F  2F90  swapc   PA.6
030  2AD0  wait0   PA.3
031  2010  t0sn    PA.0
032  C02C  goto    0x02C
033  2150  t0sn    PA.5
034  C025  goto    0x025
035  1FBC  mov     a,0xBC
036  00A0  mov     ADCC,a
037  21D0  t0sn    PA.7
038  6800  inc     M000
039  23D0  t1sn    PA.7
03A  6A00  dec     M000
03B  C023  goto    0x023
03C  6801  inc     M001
03D  5E01  mov     a,M001
03E  008B  mov     IHRCR,a
03F  C013  goto    0x013
040  008B  mov     IHRCR,a
041  0A01  ldtabh  M000
042  00B9  mov     BGTR,a

; FPPA0 User Code
043  1F00  mov     a,0x00
044  0082  mov     SP,a
045  0030  wdreset
046  0E64  delay   0x64
047  2810  tog     PA.0
048  C045  goto    0x045

; FPPA1 User Code
049  1F04  mov     a,0x04
04A  0082  mov     SP,a
04B  0EC8  delay   0xC8
04C  2850  tog     PA.1
04D  C04B  goto    0x04B
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 25, 2018, 07:54:15 pm
I think it might be better to refer to the opcodes by their symbol than their bitsize or the device
Which apparently can be different for IDE and ICE and can also be redefined in the same file (PMS150.INC for example)
The symbol files are probably also the reason why the ICE cannot assemble certain instructions and outputs NOPs instead (but probably also enables TRAP)
Unfortunately they are somewhat binary.

./PMS132.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PDK22C13.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./PMC131.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./XN1210.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC234.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PES502C.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS134.INC
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_86A
./PDK22C58A.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./PMS132B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./P201CS16A.INC
.Assembly   INSTRUMENT   SYM_83A
./PMS271.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMS150B.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PFS154.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PDK82S_EV.INC
.Assembly   INSTRUMENT   SYM_82A
./PDK82C12.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./P234C.INC
.Assembly   INSTRUMENT   SYM_83A
./P232CS20.INC
.Assembly   INSTRUMENT   SYM_83A
./PMS234.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PFC154.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC156.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PMC882.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./PDK82C13.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./XN1320B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS232.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMS154C.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./P232C.INC
.Assembly   INSTRUMENT   SYM_83A
./PMS131.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PMS155C.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC251.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMC150.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PMS154.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS156.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PES502D.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC166.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./ip5dB.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PES503.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMS155.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PDK3S_EV.INC
.Assembly   INSTRUMENT   SYM_83A
./P234CS24.INC
.Assembly   INSTRUMENT   SYM_83A
./PMS130.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PDK22C58.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./PMS171.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS171B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./MCU371.INC
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_86A
./PMR210.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_86A
./PMS165C.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS153.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PES501.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PDK_EV5.INC
.Assembly   INSTRUMENT   SYM_86A
./XN1210B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC884.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMC232.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./PMS152.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS150C.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_86A
./PMS164.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PDK22C13A.INC
.Assembly   INSTRUMENT   SYM_82A
.Assembly   ICE_INSTR   SYM_83A
./ip5dC.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_86A
./PMS132K.INC
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_86A
./XN1320D.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS133.INC
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_86A
./XN1210D.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMS154B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC153.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PFS173.INC
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_86A
./XN1210C.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PMC271.INC
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_83A
./P201CS14A.INC
.Assembly   INSTRUMENT   SYM_83A
./PMS150.INC
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
./PMS155B.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
./PES502.INC
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ICE_INSTR   SYM_86A
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 25, 2018, 08:48:12 pm
A comparison of the 13, 14, and 16 bit instruction sets.

Code: [Select]
add      a,I        1_0000_kkkk_kkkk    10_1000_kkkk_kkkk    0001_1000_kkkk_kkkk
add      a,M        0_0110_00mm_mmmm    00_1100_0mmm_mmmm    0100_001m_mmmm_mmmm
add      M,a        0_0100_00mm_mmmm    00_1000_0mmm_mmmm    0100_000m_mmmm_mmmm
addc     a          0_0000_0001_0000    00_0000_0110_0000    0000_0000_0001_0000
addc     a,M        0_0110_10mm_mmmm    00_1101_0mmm_mmmm    0100_101m_mmmm_mmmm
addc     M                              01_0000_0mmm_mmmm    0110_000m_mmmm_mmmm
addc     M,a        0_0100_10mm_mmmm    00_1001_0mmm_mmmm    0100_100m_mmmm_mmmm
and      a,I        1_0100_kkkk_kkkk    10_1100_kkkk_kkkk    0001_1100_kkkk_kkkk
and      a,M        0_0111_00mm_mmmm    00_1110_0mmm_mmmm    0101_001m_mmmm_mmmm
and      M,a        0_0101_00mm_mmmm    00_1010_0mmm_mmmm    0101_000m_mmmm_mmmm
call     label      1_11aa_aaaa_aaaa    11_1aaa_aaaa_aaaa    111a_aaaa_aaaa_aaaa
ceqsn    a,I        1_0010_kkkk_kkkk    10_1010_kkkk_kkkk    0001_1010_kkkk_kkkk
ceqsn    a,M        0_1011_10mm_mmmm    01_0111_0mmm_mmmm    0011_101m_mmmm_mmmm
ceqsn    M,a                                                 0011_100m_mmmm_mmmm
clear    M          0_1001_10mm_mmmm    01_0011_0mmm_mmmm    0110_110m_mmmm_mmmm
cneqsn   a,I                            10_1011_kkkk_kkkk    0000_0001_kkkk_kkkk
cneqsn   a,M                            01_0111_1mmm_mmmm    0001_011m_mmmm_mmmm
comp     a,I                                                 0001_1011_kkkk_kkkk
comp     a,M                            00_0110_0mmm_mmmm    0011_111m_mmmm_mmmm
comp     M,a                            00_0110_1mmm_mmmm    0011_110m_mmmm_mmmm
dec      M          0_1001_01mm_mmmm    01_0010_1mmm_mmmm    0110_101m_mmmm_mmmm
delay    a                                                   0000_0000_0001_1111
delay    I                                                   0000_1110_kkkk_kkkk
delay    M                                                   0111_111m_mmmm_mmmm
disgint             0_0000_0011_1001    00_0000_0111_1001    0000_0000_0011_1001
dzsn     a          0_0000_0001_0011    00_0000_0110_0011    0000_0000_0001_0011
dzsn     M          0_1000_11mm_mmmm    01_0001_1mmm_mmmm    0110_011m_mmmm_mmmm
engint              0_0000_0011_1000    00_0000_0111_1000    0000_0000_0011_1000
goto     label      1_10aa_aaaa_aaaa    11_0aaa_aaaa_aaaa    110a_aaaa_aaaa_aaaa
idxm     a,index    0_0000_111w_www1    00_0011_1www_www1    0000_100w_wwww_www1
idxm     index,a    0_0000_111w_www0    00_0011_1www_www0    0000_100w_wwww_www0
inc      M          0_1001_00mm_mmmm    01_0010_0mmm_mmmm    0110_100m_mmmm_mmmm
izsn     a          0_0000_0001_0010    00_0000_0110_0010    0000_0000_0001_0010
izsn     M          0_1000_10mm_mmmm    01_0001_0mmm_mmmm    0110_010m_mmmm_mmmm
ldspth                                  00_0000_0000_0111
ldsptl                                  00_0000_0000_0110
ldt16    word       0_0000_110w_www1    00_0011_0www_www1    0000_001w_wwww_www1
ldtabh   word                                                0000_101w_wwww_www1
ldtabl   word                                                0000_101w_wwww_www0
mov      a,I        1_0111_kkkk_kkkk    10_1111_kkkk_kkkk    0001_1111_kkkk_kkkk
mov      a,IO       0_0000_101p_pppp    00_0001_11pp_pppp    0000_0000_11pp_pppp
mov      a,M        0_0111_11mm_mmmm    00_1111_1mmm_mmmm    0101_111m_mmmm_mmmm
mov      IO,a       0_0000_100p_pppp    00_0001_10pp_pppp    0000_0000_10pp_pppp
mov      M,a        0_0101_11mm_mmmm    00_1011_1mmm_mmmm    0101_110m_mmmm_mmmm
mul                                     00_0000_0111_1100
nadd     a,M                            00_0111_0mmm_mmmm    0011_011m_mmmm_mmmm
nadd     M,a                            00_0111_1mmm_mmmm    0011_010m_mmmm_mmmm
neg      a          0_0000_0001_1001    00_0000_0110_1001    0000_0000_0001_1001
neg      M          0_1010_01mm_mmmm    01_0100_1mmm_mmmm    0111_001m_mmmm_mmmm
nmov     a,M                                                 0011_001m_mmmm_mmmm
nmov     M,a                                                 0011_000m_mmmm_mmmm
nop                 0_0000_0000_0000    00_0000_0000_0000    0000_0000_0000_0000
not      a          0_0000_0001_1000    00_0000_0110_1000    0000_0000_0001_1000
not      M          0_1010_00mm_mmmm    01_0100_0mmm_mmmm    0111_000m_mmmm_mmmm
or       a,I        1_0101_kkkk_kkkk    10_1101_kkkk_kkkk    0001_1101_kkkk_kkkk
or       a,M        0_0111_01mm_mmmm    00_1110_1mmm_mmmm    0101_011m_mmmm_mmmm
or       M,a        0_0101_01mm_mmmm    00_1010_1mmm_mmmm    0101_010m_mmmm_mmmm
pcadd    a          0_0000_0001_0111    00_0000_0110_0111    0000_0000_0001_0111
popaf               0_0000_0011_0011    00_0000_0111_0011    0000_0000_0011_0011
pushaf              0_0000_0011_0010    00_0000_0111_0010    0000_0000_0011_0010
reset               0_0000_0011_0101    00_0000_0111_0101    0000_0000_0011_0101
ret                 0_0000_0011_1010    00_0000_0111_1010    0000_0000_0011_1010
ret      I          0_0001_kkkk_kkkk    00_0010_kkkk_kkkk    0000_1111_kkkk_kkkk
reti                0_0000_0011_1011    00_0000_0111_1011    0000_0000_0011_1011
set0     IO.n       0_1110_bbbp_pppp    01_110b_bbpp_pppp    0010_010b_bbpp_pppp
set0     M.n        0_0011_bbb0_mmmm    10_010b_bbmm_mmmm    1010_bbbm_mmmm_mmmm
set1     IO.n       0_1111_bbbp_pppp    01_111b_bbpp_pppp    0010_011b_bbpp_pppp
set1     M.n        0_0011_bbb1_mmmm    10_011b_bbmm_mmmm    1011_bbbm_mmmm_mmmm
sl       a          0_0000_0001_1011    00_0000_0110_1011    0000_0000_0001_1011
sl       M          0_1010_11mm_mmmm    01_0101_1mmm_mmmm    0111_011m_mmmm_mmmm
slc      a          0_0000_0001_1101    00_0000_0110_1101    0000_0000_0001_1101
slc      M          0_1011_01mm_mmmm    01_0110_1mmm_mmmm    0111_101m_mmmm_mmmm
sr       a          0_0000_0001_1010    00_0000_0110_1010    0000_0000_0001_1010
sr       M          0_1010_10mm_mmmm    01_0101_0mmm_mmmm    0111_010m_mmmm_mmmm
src      a          0_0000_0001_1100    00_0000_0110_1100    0000_0000_0001_1100
src      M          0_1011_00mm_mmmm    01_0110_0mmm_mmmm    0111_100m_mmmm_mmmm
stopexe             0_0000_0011_0111    00_0000_0111_0111    0000_0000_0011_0111
stopsys             0_0000_0011_0110    00_0000_0111_0110    0000_0000_0011_0110
stt16    word       0_0000_110w_www0    00_0011_0www_www0    0000_001w_wwww_www0
sub      a,I        1_0001_kkkk_kkkk    10_1001_kkkk_kkkk    0001_1001_kkkk_kkkk
sub      a,M        0_0110_01mm_mmmm    00_1100_1mmm_mmmm    0100_011m_mmmm_mmmm
sub      M,a        0_0100_01mm_mmmm    00_1000_1mmm_mmmm    0100_010m_mmmm_mmmm
subc     a          0_0000_0001_0001    00_0000_0110_0001    0000_0000_0001_0001
subc     a,M        0_0110_11mm_mmmm    00_1101_1mmm_mmmm    0100_111m_mmmm_mmmm
subc     M                              01_0000_1mmm_mmmm    0110_001m_mmmm_mmmm
subc     M,a        0_0100_11mm_mmmm    00_1001_1mmm_mmmm    0100_110m_mmmm_mmmm
swap     a          0_0000_0001_1110    00_0000_0110_1110    0000_0000_0001_1110
swap     M                                                   0111_110m_mmmm_mmmm
swapc    IO.n                           00_010b_bbpp_pppp    0010_111b_bbpp_pppp
t0sn     IO.n       0_1100_bbbp_pppp    01_100b_bbpp_pppp    0010_000b_bbpp_pppp
t0sn     M.n        0_0010_bbb0_mmmm    10_000b_bbmm_mmmm    1000_bbbm_mmmm_mmmm
t1sn     IO.n       0_1101_bbbp_pppp    01_101b_bbpp_pppp    0010_001b_bbpp_pppp
t1sn     M.n        0_0010_bbb1_mmmm    10_001b_bbmm_mmmm    1001_bbbm_mmmm_mmmm
tog      IO.n                                                0010_100b_bbpp_pppp
wait0    IO.n                                                0010_101b_bbpp_pppp
wait1    IO.n                                                0010_110b_bbpp_pppp
wdreset             0_0000_0011_0000    00_0000_0111_0000    0000_0000_0011_0000
xch      M          0_1001_11mm_mmmm    01_0011_1mmm_mmmm    0110_111m_mmmm_mmmm
xor      a,I        1_0110_kkkk_kkkk    10_1110_kkkk_kkkk    0001_1110_kkkk_kkkk
xor      a,IO                                                0001_0000_01pp_pppp
xor      a,M        0_0111_10mm_mmmm    00_1111_0mmm_mmmm    0101_101m_mmmm_mmmm
xor      IO,a       0_0000_011p_pppp    00_0000_11pp_pppp    0001_0000_00pp_pppp
xor      M,a        0_0101_10mm_mmmm    00_1011_0mmm_mmmm    0101_100m_mmmm_mmmm

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: amyk on November 26, 2018, 02:15:08 am
No immediately discernable obvious systema to the opcode layout besides the fixed position of the address/data fields --- I'd be really curious to see a decap of these MCUs, because the randomness of the assignment means they're probably implemented directly with a PLA and no microcode nor field-specific decoding.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 26, 2018, 09:46:30 am
A comparison of the 13, 14, and 16 bit instruction sets.
[…]

You seem to be missing  few instructions in the 16-bit instruction set. In particular, I noticed pushw word, popw word, pushw pcN, popw pcN.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 26, 2018, 10:01:28 am
What chip has those instructions? I used the PMC234 as a reference and it does not have them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: mikeselectricstuff on November 26, 2018, 10:09:12 am
No immediately discernable obvious systema to the opcode layout besides the fixed position of the address/data fields --- I'd be really curious to see a decap of these MCUs, because the randomness of the assignment means they're probably implemented directly with a PLA and no microcode nor field-specific decoding.
Ken Sherriff just did a teardown and decap of a flame lamp that uses a 16-pin unmarked MCU, which may or may not be a PADUK chip. Unfortunately no schematic to compare pinouts

https://electronupdate.blogspot.com/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 26, 2018, 10:24:32 am
What chip has those instructions? I used the PMC234 as a reference and it does not have them.

I am not sure in general, but so far all the 8-core dveices that I read datasheets of have them, while the 2-core devices don't.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 26, 2018, 11:08:35 am
.CHIP PDK82S_EV made more opcodes acceptable to the assembler

Code: [Select]
0x0400  popw   word
0x0401  pushw  word
0x0060  popw   pcN
0x0070  pushw  pcN
0x003C  mul

Looking for ideas on how to get the opcodes for 13 and 16 bit ldsptl/ldspth
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 26, 2018, 11:21:20 am
pushw/popw pcN use 4 bits for the core number :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 26, 2018, 12:06:16 pm
.CHIP PDK82S_EV made more opcodes acceptable to the assembler

Code: [Select]
0x0400  popw   word
0x0401  pushw  word
0x0060  popw   pcN
0x0070  pushw  pcN
0x003C  mul

Looking for ideas on how to get the opcodes for 13 and 16 bit ldsptl/ldspth


There should also be instructions
IGOTO
ICALL
and
PMODE

The best idea I have is to look at the Symbol Files but if they encode the Opcodes as well as the mnemonics it seems to be in different places
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 26, 2018, 12:23:39 pm
Code: [Select]
0x0040  pmode   n
0x0600  igoto   word
0x0601  icall   word

Not many gaps remaining in the 16 bit instruction set
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 26, 2018, 12:45:52 pm
Code: [Select]
0x0040  pmode   n
0x0600  igoto   word
0x0601  icall   word

Not many gaps remaining in the 16 bit instruction set


True, although I would consider calling this PDK_SYM_82A instruction set.

Could you also point out what chips you used for the other instruction sets?

If I counted correctly there are only these instruction set families
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
.Assembly   INSTRUMENT   SYM_82A
.Assembly   INSTRUMENT   SYM_83A
.Assembly   INSTRUMENT   SYM_86A

I suspect that INSTRUMENT means same for ASM and ICE
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 26, 2018, 01:04:29 pm
I have a startup file for the pfs154 that doesnt dissasemble correctly using the current sets, I suspect that 85A is still different from the others
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 26, 2018, 01:54:51 pm
I started to create simple demo projects for PADAUK IDE:

- simple blink in mini-C
- simple blink in ASM embedded in mini-C
- simple blink in pure ASM
- timer based blink using interrupt

https://github.com/free-pdk/simple-pdk-code-examples

If you have analyzed some special functions please try to create a simple demo project just describing / using this function.
This will come handy for regression testing emulation.

To research:
 - watchdog
 - edge triggered interrupts for PA/PB
 - timer source PA/PB pin change
 - stopsys / stopexe and wakeup interrupt
 - adc
 - multicore
 - ...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DDunfield on November 26, 2018, 07:56:58 pm
In case anyone else wants to fool with it, I've made my *very Quick and Dirty*/preliminary simulator for the PMC150/PMS150 available on a google drive at the following link:

https://drive.google.com/open?id=1iNK7dmASzDRcld0SGHDq_lqcMhntBvrv (https://drive.google.com/open?id=1iNK7dmASzDRcld0SGHDq_lqcMhntBvrv)

Before you bother downloading it, take note:

Most of you won't like it - the main reason being that I tend to prototype software things with the tools that I am most familiar with and in this case I built it with a compiler I wrote back in the 80's, which builds DOS executables. That means you need a DOS compatible environment. For most modern 64-bit systems, DOSBOX works well, and is available for Windows/Linux/Mac/Android etc. (yeah, I can run PSM150 code on my phone!) - for Windows, I recommend the DOSBOX that I have posted under "DOS wigets" on my site (www.dunfield.com (http://www.dunfield.com)).

It is a very preliminary prototype. It is not optimized in any way.

It does not yet simulate any of the on-chip hardware (timer, interrupts etc). At this time this is for fooling with the instruction set only.

I've confirmed that it understands all the instructions listed in the PMC150/PMS150 manual, however I have not exhaustively tested them. I do not have the Paudak ICE or programmer, so I cannot easily verify the operation of the actual CPU (implementation is a combination of guesswork and "as documented" in the Paudak data sheet). There are most certainly bugs. I will update the simulator as these are found/reported. Please contact me as 'DDunfield' on the EEVBLOG forums.

Refer to the QDS150.TXT file included in the above archive for more information.

Dave
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 26, 2018, 10:20:39 pm
Hi,

I just created a repository on github containing new tools and source code for PDK FPPA controller:

https://github.com/free-pdk/fppa-pdk-tools

depdk : deobfuscate PDK file to binary format
dispdk : disassemble PDK file (the 14 bit instruction set disassembler is already working, only mapped processors are PMx154 variants)
emupdk: simulates PDK (PMx154 is implemented and mapped)

I spent quite some time with the flag solver for OV, AC, CF, ZF. But it is easy to reuse now for all other processor types.
Basic testing was done with most ALU operations so it's looking good.

-> adapting disassembler for 13/16 bit is a simple task
-> adapting emulator for 13 bit should be straight forward, 16 bit needs some understanding of new opcodes

I will focus on interrupt / peripheral emulation and GUI (ncurses).

So if anybody wants to assist, 13/16 bit needs implementation.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 27, 2018, 06:20:05 pm
Code: [Select]
0x0040  pmode   n
0x0600  igoto   word
0x0601  icall   word

Not many gaps remaining in the 16 bit instruction set


True, although I would consider calling this PDK_SYM_82A instruction set.

Could you also point out what chips you used for the other instruction sets?

If I counted correctly there are only these instruction set families
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
.Assembly   INSTRUMENT   SYM_82A
.Assembly   INSTRUMENT   SYM_83A
.Assembly   INSTRUMENT   SYM_86A

I suspect that INSTRUMENT means same for ASM and ICE

Chips settings I have used...

13 bit:  PMS150C
14 bit:  PFS154
16 bit:  PMS234  PMC882  PMC884  PDK82C12  PDK82C13  PDK82S_EV

I think the SYM_8xx designations refer to subsets of the full instruction set that run on specific hardware revs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 27, 2018, 06:22:55 pm
I have a startup file for the pfs154 that doesnt dissasemble correctly using the current sets, I suspect that 85A is still different from the others

Looks like the same 14 bit instruction set to me. What differences did you notice?

Test program
Code: [Select]
.CHIP PFS154
//{{PADAUK_CODE_OPTION
.Code_Option LVR 2.5V
.Code_Option Security Enable // Security 7/8 words Enable
.Code_Option Comparator_Edge All_Edge
.Code_Option LCD2 Disable // At ICE, LCD always disable, PB0 PA0/3/4 are independent pins
.Code_Option Bootup_Time Fast
.Code_Option Drive Normal
//}}PADAUK_CODE_OPTION

goto FPPA0

WORD Stack_FPPA0 [2]

FPPA0:
.ADJUST_IC SYSCLK=IHRC/8, IHRC=16MHz, VDD=5V

SP = Stack_FPPA0;

@@:
wdreset
nop
goto @B

Disassembly
Code: [Select]
000  3001  goto    0x001
001  2F00  mov     a,0x00
002  0182  mov     SP,a
003  3FED  call    0x7ED
004  018B  mov     IHRCR,a
005  3FEE  call    0x7EE
006  019A  mov     BGTR,a
007  2F80  mov     a,0x80
008  019B  mov     MISC_LVR,a
009  2F3C  mov     a,0x3C
00A  0183  mov     CLKCMD,a
00B  3FFE  call    0x7FE
00C  2AFF  ceqsn   a,0xFF
00D  3054  goto    0x054
00E  3FED  call    0x7ED
00F  0B81  mov     M01,a
010  1F91  set1    PAC.6
011  2F09  mov     a,0x09
012  0B80  mov     M00,a
013  1AD0  t1sn    PA.3
014  3013  goto    0x013
015  1F90  set1    PA.6
016  0063  dzsn    a
017  3016  goto    0x016
018  1180  dzsn    M00
019  3016  goto    0x016
01A  1D90  set0    PA.6
01B  18D0  t0sn    PA.3
01C  301B  goto    0x01B
01D  2F01  mov     a,0x01
01E  1950  t0sn    PA.5
01F  2FFF  mov     a,0xFF
020  0C01  add     a,M01
021  018B  mov     IHRCR,a
022  0B81  mov     M01,a
023  1AD0  t1sn    PA.3
024  3023  goto    0x023
025  1B50  t1sn    PA.5
026  304F  goto    0x04F
027  2F04  mov     a,0x04
028  0188  mov     MISC,a
029  18D0  t0sn    PA.3
02A  3029  goto    0x029
02B  2F02  mov     a,0x02
02C  0182  mov     SP,a
02D  1304  clear   M04
02E  1305  clear   M05
02F  2F59  mov     a,0x59
030  0B82  mov     M02,a
031  2F00  mov     a,0x00
032  0B83  mov     M03,a
033  0006  ldsptl
034  0B04  xor     M04,a
035  0007  ldspth
036  0805  add     M05,a
037  1584  sl      M04
038  1685  slc     M05
039  1004  addc    M04
03A  1282  dec     M02
03B  1083  subc    M03
03C  1A40  t1sn    FLAG.1
03D  3033  goto    0x033
03E  1F90  set1    PA.6
03F  1AD0  t1sn    PA.3
040  303F  goto    0x03F
041  1584  sl      M04
042  1685  slc     M05
043  0590  swapc   PA.6
044  18D0  t0sn    PA.3
045  3044  goto    0x044
046  1950  t0sn    PA.5
047  303F  goto    0x03F
048  1D90  set0    PA.6
049  1AD0  t1sn    PA.3
04A  3049  goto    0x049
04B  18D0  t0sn    PA.3
04C  304B  goto    0x04B
04D  1B50  t1sn    PA.5
04E  302B  goto    0x02B
04F  18D0  t0sn    PA.3
050  304F  goto    0x04F
051  1B50  t1sn    PA.5
052  3011  goto    0x011
053  3053  goto    0x053
054  018B  mov     IHRCR,a
055  2F00  mov     a,0x00
056  0182  mov     SP,a
057  0070  wdreset
058  0000  nop
059  3057  goto    0x057
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on November 27, 2018, 06:51:18 pm
Updated instruction set encodings. Sorted by opcode. All gaps indicated.

16 bit
Code: [Select]
0x0000  0000_0000_0000_0000  nop
0x0001  0000_0000_0000_0001
0x0002  0000_0000_0000_0010
0x0003  0000_0000_0000_0011
0x0004  0000_0000_0000_0100
0x0005  0000_0000_0000_0101
0x0006  0000_0000_0000_0110
0x0007  0000_0000_0000_0111
0x0008  0000_0000_0000_1000
0x0009  0000_0000_0000_1001
0x000A  0000_0000_0000_1010
0x000B  0000_0000_0000_1011
0x000C  0000_0000_0000_1100
0x000D  0000_0000_0000_1101
0x000E  0000_0000_0000_1110
0x000F  0000_0000_0000_1111
0x0010  0000_0000_0001_0000  addc     a
0x0011  0000_0000_0001_0001  subc     a
0x0012  0000_0000_0001_0010  izsn     a
0x0013  0000_0000_0001_0011  dzsn     a
0x0014  0000_0000_0001_0100
0x0015  0000_0000_0001_0101
0x0016  0000_0000_0001_0110
0x0017  0000_0000_0001_0111  pcadd    a
0x0018  0000_0000_0001_1000  not      a
0x0019  0000_0000_0001_1001  neg      a
0x001A  0000_0000_0001_1010  sr       a
0x001B  0000_0000_0001_1011  sl       a
0x001C  0000_0000_0001_1100  src      a
0x001D  0000_0000_0001_1101  slc      a
0x001E  0000_0000_0001_1110  swap     a
0x001F  0000_0000_0001_1111  delay    a
0x0020  0000_0000_0010_----
0x0030  0000_0000_0011_0000  wdreset
0x0031  0000_0000_0011_0001
0x0032  0000_0000_0011_0010  pushaf
0x0033  0000_0000_0011_0011  popaf
0x0034  0000_0000_0011_0100
0x0035  0000_0000_0011_0101  reset
0x0036  0000_0000_0011_0110  stopsys
0x0037  0000_0000_0011_0111  stopexe
0x0038  0000_0000_0011_1000  engint
0x0039  0000_0000_0011_1001  disgint
0x003A  0000_0000_0011_1010  ret
0x003B  0000_0000_0011_1011  reti
0x003C  0000_0000_0011_1100  mul
0x003D  0000_0000_0011_1101
0x003E  0000_0000_0011_1110
0x003F  0000_0000_0011_1111
0x0040  0000_0000_010k_kkkk  pmode    n
0x0060  0000_0000_0110_tttt  popw     pcN
0x0070  0000_0000_0111_tttt  pushw    pcN
0x0080  0000_0000_10pp_pppp  mov      IO,a
0x00C0  0000_0000_11pp_pppp  mov      a,IO
0x0100  0000_0001_kkkk_kkkk  cneqsn   a,I
0x0200  0000_001w_wwww_www0  stt16    word
0x0201  0000_001w_wwww_www1  ldt16    word
0x0400  0000_010w_wwww_www0  popw     word
0x0401  0000_010w_wwww_www1  pushw    word
0x0600  0000_011w_wwww_www0  igoto    word
0x0601  0000_011w_wwww_www1  icall    word
0x0800  0000_100w_wwww_www0  idxm     index,a
0x0801  0000_100w_wwww_www1  idxm     a,index
0x0A00  0000_101w_wwww_www0  ldtabl   word
0x0A01  0000_101w_wwww_www1  ldtabh   word
0x0C00  0000_110-_----_----
0x0E00  0000_1110_kkkk_kkkk  delay    I
0x0F00  0000_1111_kkkk_kkkk  ret      I
0x1000  0001_0000_00pp_pppp  xor      IO,a
0x1040  0001_0000_01pp_pppp  xor      a,IO
0x1080  0001_0000_1---_----
0x1100 0001_0001_----_----
0x1200 0001_001-_----_----
0x1400 0001_010m_mmmm_mmmm  cneqsn   M,a
0x1600  0001_011m_mmmm_mmmm  cneqsn   a,M
0x1800  0001_1000_kkkk_kkkk  add      a,I
0x1900  0001_1001_kkkk_kkkk  sub      a,I
0x1A00  0001_1010_kkkk_kkkk  ceqsn    a,I
0x1B00  0001_1011_kkkk_kkkk  comp     a,I
0x1C00  0001_1100_kkkk_kkkk  and      a,I
0x1D00  0001_1101_kkkk_kkkk  or       a,I
0x1E00  0001_1110_kkkk_kkkk  xor      a,I
0x1F00  0001_1111_kkkk_kkkk  mov      a,I
0x2000  0010_000b_bbpp_pppp  t0sn     IO.n
0x2200  0010_001b_bbpp_pppp  t1sn     IO.n
0x2400  0010_010b_bbpp_pppp  set0     IO.n
0x2600  0010_011b_bbpp_pppp  set1     IO.n
0x2800  0010_100b_bbpp_pppp  tog      IO.n
0x2A00  0010_101b_bbpp_pppp  wait0    IO.n
0x2C00  0010_110b_bbpp_pppp  wait1    IO.n
0x2E00  0010_111b_bbpp_pppp  swapc    IO.n
0x3000  0011_000m_mmmm_mmmm  nmov     M,a
0x3200  0011_001m_mmmm_mmmm  nmov     a,M
0x3400  0011_010m_mmmm_mmmm  nadd     M,a
0x3600  0011_011m_mmmm_mmmm  nadd     a,M
0x3800  0011_100m_mmmm_mmmm  ceqsn    M,a
0x3A00  0011_101m_mmmm_mmmm  ceqsn    a,M
0x3C00  0011_110m_mmmm_mmmm  comp     M,a
0x3E00  0011_111m_mmmm_mmmm  comp     a,M
0x4000  0100_000m_mmmm_mmmm  add      M,a
0x4200  0100_001m_mmmm_mmmm  add      a,M
0x4400  0100_010m_mmmm_mmmm  sub      M,a
0x4600  0100_011m_mmmm_mmmm  sub      a,M
0x4800  0100_100m_mmmm_mmmm  addc     M,a
0x4A00  0100_101m_mmmm_mmmm  addc     a,M
0x4C00  0100_110m_mmmm_mmmm  subc     M,a
0x4E00  0100_111m_mmmm_mmmm  subc     a,M
0x5000  0101_000m_mmmm_mmmm  and      M,a
0x5200  0101_001m_mmmm_mmmm  and      a,M
0x5400  0101_010m_mmmm_mmmm  or       M,a
0x5600  0101_011m_mmmm_mmmm  or       a,M
0x5800  0101_100m_mmmm_mmmm  xor      M,a
0x5A00  0101_101m_mmmm_mmmm  xor      a,M
0x5C00  0101_110m_mmmm_mmmm  mov      M,a
0x5E00  0101_111m_mmmm_mmmm  mov      a,M
0x6000  0110_000m_mmmm_mmmm  addc     M
0x6200  0110_001m_mmmm_mmmm  subc     M
0x6400  0110_010m_mmmm_mmmm  izsn     M
0x6600  0110_011m_mmmm_mmmm  dzsn     M
0x6800  0110_100m_mmmm_mmmm  inc      M
0x6A00  0110_101m_mmmm_mmmm  dec      M
0x6C00  0110_110m_mmmm_mmmm  clear    M
0x6E00  0110_111m_mmmm_mmmm  xch      M
0x7000  0111_000m_mmmm_mmmm  not      M
0x7200  0111_001m_mmmm_mmmm  neg      M
0x7400  0111_010m_mmmm_mmmm  sr       M
0x7600  0111_011m_mmmm_mmmm  sl       M
0x7800  0111_100m_mmmm_mmmm  src      M
0x7A00  0111_101m_mmmm_mmmm  slc      M
0x7C00  0111_110m_mmmm_mmmm  swap     M
0x7E00  0111_111m_mmmm_mmmm  delay    M
0x8000  1000_bbbm_mmmm_mmmm  t0sn     M.n
0x9000  1001_bbbm_mmmm_mmmm  t1sn     M.n
0xA000  1010_bbbm_mmmm_mmmm  set0     M.n
0xB000  1011_bbbm_mmmm_mmmm  set1     M.n
0xC000  110a_aaaa_aaaa_aaaa  goto     label
0xE000  111a_aaaa_aaaa_aaaa  call     label


14 bit
Code: [Select]
0x0000  00_0000_0000_0000   nop
0x0001  00_0000_0000_0001
0x0002  00_0000_0000_0010
0x0003  00_0000_0000_0011
0x0004  00_0000_0000_0100
0x0005  00_0000_0000_0101
0x0006  00_0000_0000_0110   ldsptl         
0x0007  00_0000_0000_0111   ldspth         
0x0008  00_0000_0000_1---
0x0010  00_0000_0001_----
0x0020  00_0000_001-_----
0x0040  00_0000_010-_----
0x0060  00_0000_0110_0000   addc    a       
0x0061  00_0000_0110_0001   subc    a       
0x0062  00_0000_0110_0010   izsn    a       
0x0063  00_0000_0110_0011   dzsn    a       
0x0064  00_0000_0110_0100
0x0065  00_0000_0110_0101
0x0066  00_0000_0110_0110
0x0067  00_0000_0110_0111   pcadd   a       
0x0068  00_0000_0110_1000   not     a       
0x0069  00_0000_0110_1001   neg     a       
0x006a  00_0000_0110_1010   sr      a       
0x006b  00_0000_0110_1011   sl      a       
0x006c  00_0000_0110_1100   src     a       
0x006d  00_0000_0110_1101   slc     a       
0x006e  00_0000_0110_1110   swap    a       
0x006f  00_0000_0110_1111
0x0070  00_0000_0111_0000   wdreset         
0x0071  00_0000_0111_0001
0x0072  00_0000_0111_0010   pushaf         
0x0073  00_0000_0111_0011   popaf           
0x0074  00_0000_0111_0100
0x0075  00_0000_0111_0101   reset           
0x0076  00_0000_0111_0110   stopsys         
0x0077  00_0000_0111_0111   stopexe         
0x0078  00_0000_0111_1000   engint         
0x0079  00_0000_0111_1001   disgint         
0x007a  00_0000_0111_1010   ret             
0x007b  00_0000_0111_1011   reti           
0x007c  00_0000_0111_1100   mul             
0x007d  00_0000_0111_1101
0x007e  00_0000_0111_1110
0x007f  00_0000_0111_1111
0x0080  00_0000_10--_----
0x00c0  00_0000_11pp_pppp   xor     io,a   
0x0100  00_0001_00--_----
0x0140  00_0001_01--_----
0x0180  00_0001_10pp_pppp   mov     io,a   
0x01c0  00_0001_11pp_pppp   mov     a,io   
0x0200  00_0010_kkkk_kkkk   ret     k       
0x0300  00_0011_0aaa_aaa0   stt16   m       
0x0301  00_0011_0aaa_aaa1   ldt16   m       
0x0380  00_0011_1aaa_aaa0   idxm    m,a     
0x0381  00_0011_1aaa_aaa1   idxm    a,m     
0x0400  00_010b_bbpp_pppp   swapc   io.b   
0x0600  00_0110_0aaa_aaaa   comp    a,m     
0x0680  00_0110 1aaa_aaaa   comp    m,a     
0x0700  00_0111_0aaa_aaaa   nadd    a,m     
0x0780  00_0111_1aaa_aaaa   nadd    m,a     
0x0800  00_1000_0aaa_aaaa   add     m,a     
0x0880  00_1000_1aaa_aaaa   sub     m,a     
0x0900  00_1001_0aaa_aaaa   addc    m,a     
0x0980  00_1001_1aaa_aaaa   subc    m,a     
0x0a00  00_1010_0aaa_aaaa   and     m,a     
0x0a80  00_1010_1aaa_aaaa   or      m,a     
0x0b00  00_1011_0aaa_aaaa   xor     m,a     
0x0b80  00_1011_1aaa_aaaa   mov     m,a     
0x0c00  00_1100_0aaa_aaaa   add     a,m     
0x0c80  00_1100_1aaa_aaaa   sub     a,m     
0x0d00  00_1101_0aaa_aaaa   addc    a,m     
0x0d80  00_1101_1aaa_aaaa   subc    a,m     
0x0e00  00_1110_0aaa_aaaa   and     a,m     
0x0e80  00_1110_1aaa_aaaa   or      a,m     
0x0f00  00_1111_0aaa_aaaa   xor     a,m     
0x0f80  00_1111_1aaa_aaaa   mov     a,m     
0x1000  01_0000_0aaa_aaaa   addc    m       
0x1080  01_0000_1aaa_aaaa   subc    m       
0x1100  01_0001_0aaa_aaaa   izsn    m       
0x1180  01_0001_1aaa_aaaa   dzsn    m       
0x1200  01_0010_0aaa_aaaa   inc     m       
0x1280  01_0010_1aaa_aaaa   dec     m       
0x1300  01_0011_0aaa_aaaa   clear   m       
0x1380  01_0011_1aaa_aaaa   xch     m       
0x1400  01_0100_0aaa_aaaa   not     m       
0x1480  01_0100_1aaa_aaaa   neg     m       
0x1500  01_0101_0aaa_aaaa   sr      m       
0x1580  01_0101_1aaa_aaaa   sl      m       
0x1600  01_0110_0aaa_aaaa   src     m       
0x1680  01_0110_1aaa_aaaa   slc     m       
0x1700  01_0111_0aaa_aaaa   ceqsn   a,m     
0x1780  01_0111_1aaa_aaaa   cneqsn  a,m     
0x1800  01_100b_bbpp_pppp   t0sn    io.b   
0x1a00  01_101b_bbpp_pppp   t1sn    io.b   
0x1c00  01_110b_bbpp_pppp   set0    io.b   
0x1e00  01_111b_bbpp_pppp   set1    io.b   
0x2000  10_000b_bbaa_aaaa   t0sn    m.b     
0x2200  10_001b_bbaa_aaaa   t1sn    m.b     
0x2400  10_010b_bbaa_aaaa   set0    m.b     
0x2600  10_011b_bbaa_aaaa   set1    m.b     
0x2800  10_1000_dddd_dddd   add     a,k     
0x2900  10_1001_dddd_dddd   sub     a,k     
0x2a00  10_1010_dddd_dddd   ceqsn   a,k     
0x2b00  10_1011_dddd_dddd   cneqsn  a,k     
0x2c00  10_1100_dddd_dddd   and     a,k     
0x2d00  10_1101_dddd_dddd   or      a,k     
0x2e00  10_1110_dddd_dddd   xor     a,k     
0x2f00  10_1111_dddd_dddd   mov     a,k     
0x3000  11_0aaa_aaaa_aaaa   goto    k       
0x3800  11_1aaa_aaaa_aaaa   call    k       


13 bit
Code: [Select]
0x0000 0_0000_0000_0000  nop
0x0001 0_0000_0000_0001 
0x0002 0_0000_0000_0010 
0x0003 0_0000_0000_0011 
0x0004 0_0000_0000_0100 
0x0005 0_0000_0000_0101 
0x0006 0_0000_0000_0110 
0x0007 0_0000_0000_0111 
0x0008 0_0000_0000_1000 
0x0009 0_0000_0000_1001 
0x000a 0_0000_0000_1010 
0x000b 0_0000_0000_1011 
0x000c 0_0000_0000_1100 
0x000d 0_0000_0000_1101 
0x000e 0_0000_0000_1110 
0x000f 0_0000_0000_1111 
0x0010 0_0000_0001_0000  addc      a
0x0011 0_0000_0001_0001  subc      a
0x0012 0_0000_0001_0010  izsn      a
0x0013 0_0000_0001_0011  dzsn      a
0x0014 0_0000_0001_0100 
0x0015 0_0000_0001_0101 
0x0016 0_0000_0001_0110 
0x0017 0_0000_0001_0111  pcadd     a
0x0018 0_0000_0001_1000  not       a
0x0019 0_0000_0001_1001  neg       a
0x001a 0_0000_0001_1010  sr        a
0x001b 0_0000_0001_1011  sl        a
0x001c 0_0000_0001_1100  src       a
0x001d 0_0000_0001_1101  slc       a
0x001e 0_0000_0001_1110  swap      a
0x001f 0_0000_0001_1111 
0x0020 0_0000_0010_---- 
0x0030 0_0000_0011_0000  wdreset
0x0031 0_0000_0011_0001 
0x0032 0_0000_0011_0010  pushaf
0x0033 0_0000_0011_0011  popaf
0x0034 0_0000_0011_0100 
0x0035 0_0000_0011_0101  reset
0x0036 0_0000_0011_0110  stopsys
0x0037 0_0000_0011_0111  stopexe
0x0038 0_0000_0011_1000  engint
0x0039 0_0000_0011_1001  disgint
0x003a 0_0000_0011_1010  ret
0x003b 0_0000_0011_1011  reti
0x003c 0_0000_0011_1100 
0x003d 0_0000_0011_1101 
0x003e 0_0000_0011_1110 
0x003f 0_0000_0011_1111 
0x0040 0_0000_010-_---- 
0x0060 0_0000_011p_pppp  xor       io,a
0x0080 0_0000_100p_pppp  mov       io,a
0x00a0 0_0000_101p_pppp  mov       a,io
0x00c0 0_0000_110a_aaa0  stt16     m
0x00c1 0_0000_110a_aaa1  ldt16     m
0x00e0 0_0000_111a_aaa0  idxm      m,a
0x00e1 0_0000_111a_aaa1  idxm      a,m
0x0100 0_0001_dddd_dddd  ret       k
0x0200 0_0010_bbb0_aaaa  t0sn      m.b
0x0210 0_0010_bbb1_aaaa  t1sn      m.b
0x0300 0_0011_bbb0_aaaa  set0      m.b
0x0310 0_0011_bbb1_aaaa  set1      m.b
0x0400 0_0100_00aa_aaaa  add       m,a
0x0440 0_0100_01aa_aaaa  sub       m,a
0x0480 0_0100_10aa_aaaa  addc      m,a
0x04c0 0_0100_11aa_aaaa  subc      m,a
0x0500 0_0101_00aa_aaaa  and       m,a
0x0540 0_0101_01aa_aaaa  or        m,a
0x0580 0_0101_10aa_aaaa  xor       m,a
0x05c0 0_0101_11aa_aaaa  mov       m,a
0x0600 0_0110_00aa_aaaa  add       a,m
0x0640 0_0110_01aa_aaaa  sub       a,m
0x0680 0_0110_10aa_aaaa  addc      a,m
0x06c0 0_0110_11aa_aaaa  subc      a,m
0x0700 0_0111_00aa_aaaa  and       a,m
0x0740 0_0111_01aa_aaaa  or        a,m
0x0780 0_0111_10aa_aaaa  xor       a,m
0x07c0 0_0111_11aa_aaaa  mov       a,m
0x0800 0_1000_00aa_aaaa  addc      m
0x0840 0_1000_01aa_aaaa  subc      m
0x0880 0_1000_10aa_aaaa  izsn      m
0x08c0 0_1000_11aa_aaaa  dzsn      m
0x0900 0_1001_00aa_aaaa  inc       m
0x0940 0_1001_01aa_aaaa  dec       m
0x0980 0_1001_10aa_aaaa  clear     m
0x09c0 0_1001_11aa_aaaa  xch       m
0x0a00 0_1010_00aa_aaaa  not       m
0x0a40 0_1010_01aa_aaaa  neg       m
0x0a80 0_1010_10aa_aaaa  sr        m
0x0ac0 0_1010_11aa_aaaa  sl        m
0x0b00 0_1011_00aa_aaaa  src       m
0x0b40 0_1011_01aa_aaaa  slc       m
0x0b80 0_1011_10aa_aaaa  ceqsn     a,m
0x0bc0 0_1011_11aa_aaaa  cneqsn    a,m
0x0c00 0_1100_bbbp_pppp  t0sn      p.b
0x0d00 0_1101_bbbp_pppp  t1sn      p.b
0x0e00 0_1110_bbbp_pppp  set0      p.b
0x0f00 0_1111_bbbp_pppp  set1      p.b
0x1000 1_0000_dddd_dddd  add       a,k
0x1100 1_0001_dddd_dddd  sub       a,k
0x1200 1_0010_dddd_dddd  ceqsn     a,k
0x1300 1_0011_dddd_dddd  cneqsn    a,k
0x1400 1_0100_dddd_dddd  and       a,k
0x1500 1_0101_dddd_dddd  or        a,k
0x1600 1_0110_dddd_dddd  xor       a,k
0x1700 1_0111_dddd_dddd  mov       a,k
0x1800 1_10aa_aaaa_aaaa  goto      j
0x1c00 1_11aa_aaaa_aaaa  call      j


Comparison sorted by 16 bit opcode
Code: [Select]
nop                 0000_0000_0000_0000   00_0000_0000_0000   0_0000_0000_0000
ldsptl                                    00_0000_0000_0110
ldspth                                    00_0000_0000_0111
addc      a         0000_0000_0001_0000   00_0000_0110_0000   0_0000_0001_0000
subc      a         0000_0000_0001_0001   00_0000_0110_0001   0_0000_0001_0001
izsn      a         0000_0000_0001_0010   00_0000_0110_0010   0_0000_0001_0010
dzsn      a         0000_0000_0001_0011   00_0000_0110_0011   0_0000_0001_0011
pcadd     a         0000_0000_0001_0111   00_0000_0110_0111   0_0000_0001_0111
not       a         0000_0000_0001_1000   00_0000_0110_1000   0_0000_0001_1000
neg       a         0000_0000_0001_1001   00_0000_0110_1001   0_0000_0001_1001
sr        a         0000_0000_0001_1010   00_0000_0110_1010   0_0000_0001_1010
sl        a         0000_0000_0001_1011   00_0000_0110_1011   0_0000_0001_1011
src       a         0000_0000_0001_1100   00_0000_0110_1100   0_0000_0001_1100
slc       a         0000_0000_0001_1101   00_0000_0110_1101   0_0000_0001_1101
swap      a         0000_0000_0001_1110   00_0000_0110_1110   0_0000_0001_1110
delay     a         0000_0000_0001_1111
wdreset             0000_0000_0011_0000   00_0000_0111_0000   0_0000_0011_0000
pushaf              0000_0000_0011_0010   00_0000_0111_0010   0_0000_0011_0010
popaf               0000_0000_0011_0011   00_0000_0111_0011   0_0000_0011_0011
reset               0000_0000_0011_0101   00_0000_0111_0101   0_0000_0011_0101
stopsys             0000_0000_0011_0110   00_0000_0111_0110   0_0000_0011_0110
stopexe             0000_0000_0011_0111   00_0000_0111_0111   0_0000_0011_0111
engint              0000_0000_0011_1000   00_0000_0111_1000   0_0000_0011_1000
disgint             0000_0000_0011_1001   00_0000_0111_1001   0_0000_0011_1001
ret                 0000_0000_0011_1010   00_0000_0111_1010   0_0000_0011_1010
reti                0000_0000_0011_1011   00_0000_0111_1011   0_0000_0011_1011
mul                 0000_0000_0011_1100   00_0000_0111_1100
pmode     n         0000_0000_010k_kkkk
popw      pcN       0000_0000_0110_tttt
pushw     pcN       0000_0000_0111_tttt
mov       IO,a      0000_0000_10pp_pppp   00_0001_10pp_pppp   0_0000_100p_pppp
mov       a,IO      0000_0000_11pp_pppp   00_0001_11pp_pppp   0_0000_101p_pppp
cneqsn    a,I       0000_0001_kkkk_kkkk   10_1011_kkkk_kkkk   1_0011_kkkk_kkkk
stt16     word      0000_001w_wwww_www0   00_0011_0www_www0   0_0000_110w_www0
ldt16     word      0000_001w_wwww_www1   00_0011_0www_www1   0_0000_110w_www1
popw      word      0000_010w_wwww_www0
pushw     word      0000_010w_wwww_www1
igoto     word      0000_011w_wwww_www0
icall     word      0000_011w_wwww_www1
idxm      index,a   0000_100w_wwww_www0   00_0011_1www_www0   0_0000_111w_www0
idxm      a,index   0000_100w_wwww_www1   00_0011_1www_www1   0_0000_111w_www1
ldtabl    word      0000_101w_wwww_www0
ldtabh    word      0000_101w_wwww_www1
delay     I         0000_1110_kkkk_kkkk
ret       I         0000_1111_kkkk_kkkk   00_0010_kkkk_kkkk   0_0001_kkkk_kkkk
xor       IO,a      0001_0000_00pp_pppp   00_0000_11pp_pppp   0_0000_011p_pppp
xor       a,IO      0001_0000_01pp_pppp
cneqsn    M,a       0001_010m_mmmm_mmmm
cneqsn    a,M       0001_011m_mmmm_mmmm   01_0111_1mmm_mmmm   0_1011_11mm_mmmm
add       a,I       0001_1000_kkkk_kkkk   10_1000_kkkk_kkkk   1_0000_kkkk_kkkk
sub       a,I       0001_1001_kkkk_kkkk   10_1001_kkkk_kkkk   1_0001_kkkk_kkkk
ceqsn     a,I       0001_1010_kkkk_kkkk   10_1010_kkkk_kkkk   1_0010_kkkk_kkkk
comp      a,I       0001_1011_kkkk_kkkk
and       a,I       0001_1100_kkkk_kkkk   10_1100_kkkk_kkkk   1_0100_kkkk_kkkk
or        a,I       0001_1101_kkkk_kkkk   10_1101_kkkk_kkkk   1_0101_kkkk_kkkk
xor       a,I       0001_1110_kkkk_kkkk   10_1110_kkkk_kkkk   1_0110_kkkk_kkkk
mov       a,I       0001_1111_kkkk_kkkk   10_1111_kkkk_kkkk   1_0111_kkkk_kkkk
t0sn      IO.n      0010_000b_bbpp_pppp   01_100b_bbpp_pppp   0_1100_bbbp_pppp
t1sn      IO.n      0010_001b_bbpp_pppp   01_101b_bbpp_pppp   0_1101_bbbp_pppp
set0      IO.n      0010_010b_bbpp_pppp   01_110b_bbpp_pppp   0_1110_bbbp_pppp
set1      IO.n      0010_011b_bbpp_pppp   01_111b_bbpp_pppp   0_1111_bbbp_pppp
tog       IO.n      0010_100b_bbpp_pppp
wait0     IO.n      0010_101b_bbpp_pppp
wait1     IO.n      0010_110b_bbpp_pppp
swapc     IO.n      0010_111b_bbpp_pppp   00_010b_bbpp_pppp
nmov      M,a       0011_000m_mmmm_mmmm
nmov      a,M       0011_001m_mmmm_mmmm
nadd      M,a       0011_010m_mmmm_mmmm   00_0111_1mmm_mmmm
nadd      a,M       0011_011m_mmmm_mmmm   00_0111_0mmm_mmmm
ceqsn     M,a       0011_100m_mmmm_mmmm
ceqsn     a,M       0011_101m_mmmm_mmmm   01_0111_0mmm_mmmm   0_1011_10mm_mmmm
comp      M,a       0011_110m_mmmm_mmmm   00_0110_1mmm_mmmm
comp      a,M       0011_111m_mmmm_mmmm   00_0110_0mmm_mmmm
add       M,a       0100_000m_mmmm_mmmm   00_1000_0mmm_mmmm   0_0100_00mm_mmmm
add       a,M       0100_001m_mmmm_mmmm   00_1100_0mmm_mmmm   0_0110_00mm_mmmm
sub       M,a       0100_010m_mmmm_mmmm   00_1000_1mmm_mmmm   0_0100_01mm_mmmm
sub       a,M       0100_011m_mmmm_mmmm   00_1100_1mmm_mmmm   0_0110_01mm_mmmm
addc      M,a       0100_100m_mmmm_mmmm   00_1001_0mmm_mmmm   0_0100_10mm_mmmm
addc      a,M       0100_101m_mmmm_mmmm   00_1101_0mmm_mmmm   0_0110_10mm_mmmm
subc      M,a       0100_110m_mmmm_mmmm   00_1001_1mmm_mmmm   0_0100_11mm_mmmm
subc      a,M       0100_111m_mmmm_mmmm   00_1101_1mmm_mmmm   0_0110_11mm_mmmm
and       M,a       0101_000m_mmmm_mmmm   00_1010_0mmm_mmmm   0_0101_00mm_mmmm
and       a,M       0101_001m_mmmm_mmmm   00_1110_0mmm_mmmm   0_0111_00mm_mmmm
or        M,a       0101_010m_mmmm_mmmm   00_1010_1mmm_mmmm   0_0101_01mm_mmmm
or        a,M       0101_011m_mmmm_mmmm   00_1110_1mmm_mmmm   0_0111_01mm_mmmm
xor       M,a       0101_100m_mmmm_mmmm   00_1011_0mmm_mmmm   0_0101_10mm_mmmm
xor       a,M       0101_101m_mmmm_mmmm   00_1111_0mmm_mmmm   0_0111_10mm_mmmm
mov       M,a       0101_110m_mmmm_mmmm   00_1011_1mmm_mmmm   0_0101_11mm_mmmm
mov       a,M       0101_111m_mmmm_mmmm   00_1111_1mmm_mmmm   0_0111_11mm_mmmm
addc      M         0110_000m_mmmm_mmmm   01_0000_0mmm_mmmm   0_1000_00mm_mmmm
subc      M         0110_001m_mmmm_mmmm   01_0000_1mmm_mmmm   0_1000_01mm_mmmm
izsn      M         0110_010m_mmmm_mmmm   01_0001_0mmm_mmmm   0_1000_10mm_mmmm
dzsn      M         0110_011m_mmmm_mmmm   01_0001_1mmm_mmmm   0_1000_11mm_mmmm
inc       M         0110_100m_mmmm_mmmm   01_0010_0mmm_mmmm   0_1001_00mm_mmmm
dec       M         0110_101m_mmmm_mmmm   01_0010_1mmm_mmmm   0_1001_01mm_mmmm
clear     M         0110_110m_mmmm_mmmm   01_0011_0mmm_mmmm   0_1001_10mm_mmmm
xch       M         0110_111m_mmmm_mmmm   01_0011_1mmm_mmmm   0_1001_11mm_mmmm
not       M         0111_000m_mmmm_mmmm   01_0100_0mmm_mmmm   0_1010_00mm_mmmm
neg       M         0111_001m_mmmm_mmmm   01_0100_1mmm_mmmm   0_1010_01mm_mmmm
sr        M         0111_010m_mmmm_mmmm   01_0101_0mmm_mmmm   0_1010_10mm_mmmm
sl        M         0111_011m_mmmm_mmmm   01_0101_1mmm_mmmm   0_1010_11mm_mmmm
src       M         0111_100m_mmmm_mmmm   01_0110_0mmm_mmmm   0_1011_00mm_mmmm
slc       M         0111_101m_mmmm_mmmm   01_0110_1mmm_mmmm   0_1011_01mm_mmmm
swap      M         0111_110m_mmmm_mmmm
delay     M         0111_111m_mmmm_mmmm
t0sn      M.n       1000_bbbm_mmmm_mmmm   10_000b_bbmm_mmmm   0_0010_bbb0_mmmm
t1sn      M.n       1001_bbbm_mmmm_mmmm   10_001b_bbmm_mmmm   0_0010_bbb1_mmmm
set0      M.n       1010_bbbm_mmmm_mmmm   10_010b_bbmm_mmmm   0_0011_bbb0_mmmm
set1      M.n       1011_bbbm_mmmm_mmmm   10_011b_bbmm_mmmm   0_0011_bbb1_mmmm
goto      label     110a_aaaa_aaaa_aaaa   11_0aaa_aaaa_aaaa   1_10aa_aaaa_aaaa
call      label     111a_aaaa_aaaa_aaaa   11_1aaa_aaaa_aaaa   1_11aa_aaaa_aaaa


Comparison sorted by mnemonic
Code: [Select]
add       a,I       0001_1000_kkkk_kkkk   10_1000_kkkk_kkkk   1_0000_kkkk_kkkk
add       a,M       0100_001m_mmmm_mmmm   00_1100_0mmm_mmmm   0_0110_00mm_mmmm
add       M,a       0100_000m_mmmm_mmmm   00_1000_0mmm_mmmm   0_0100_00mm_mmmm
addc      a         0000_0000_0001_0000   00_0000_0110_0000   0_0000_0001_0000
addc      a,M       0100_101m_mmmm_mmmm   00_1101_0mmm_mmmm   0_0110_10mm_mmmm
addc      M         0110_000m_mmmm_mmmm   01_0000_0mmm_mmmm   0_1000_00mm_mmmm
addc      M,a       0100_100m_mmmm_mmmm   00_1001_0mmm_mmmm   0_0100_10mm_mmmm
and       a,I       0001_1100_kkkk_kkkk   10_1100_kkkk_kkkk   1_0100_kkkk_kkkk
and       a,M       0101_001m_mmmm_mmmm   00_1110_0mmm_mmmm   0_0111_00mm_mmmm
and       M,a       0101_000m_mmmm_mmmm   00_1010_0mmm_mmmm   0_0101_00mm_mmmm
call      label     111a_aaaa_aaaa_aaaa   11_1aaa_aaaa_aaaa   1_11aa_aaaa_aaaa
ceqsn     a,I       0001_1010_kkkk_kkkk   10_1010_kkkk_kkkk   1_0010_kkkk_kkkk
ceqsn     a,M       0011_101m_mmmm_mmmm   01_0111_0mmm_mmmm   0_1011_10mm_mmmm
ceqsn     M,a       0011_100m_mmmm_mmmm
clear     M         0110_110m_mmmm_mmmm   01_0011_0mmm_mmmm   0_1001_10mm_mmmm
cneqsn    a,I       0000_0001_kkkk_kkkk   10_1011_kkkk_kkkk   1_0011_kkkk_kkkk
cneqsn    a,M       0001_011m_mmmm_mmmm   01_0111_1mmm_mmmm   0_1011_11mm_mmmm
cneqsn    M,a       0001_010m_mmmm_mmmm
comp      a,I       0001_1011_kkkk_kkkk
comp      a,M       0011_111m_mmmm_mmmm   00_0110_0mmm_mmmm
comp      M,a       0011_110m_mmmm_mmmm   00_0110_1mmm_mmmm
dec       M         0110_101m_mmmm_mmmm   01_0010_1mmm_mmmm   0_1001_01mm_mmmm
delay     a         0000_0000_0001_1111
delay     I         0000_1110_kkkk_kkkk
delay     M         0111_111m_mmmm_mmmm
disgint             0000_0000_0011_1001   00_0000_0111_1001   0_0000_0011_1001
dzsn      a         0000_0000_0001_0011   00_0000_0110_0011   0_0000_0001_0011
dzsn      M         0110_011m_mmmm_mmmm   01_0001_1mmm_mmmm   0_1000_11mm_mmmm
engint              0000_0000_0011_1000   00_0000_0111_1000   0_0000_0011_1000
goto      label     110a_aaaa_aaaa_aaaa   11_0aaa_aaaa_aaaa   1_10aa_aaaa_aaaa
icall     word      0000_011w_wwww_www1
idxm      a,index   0000_100w_wwww_www1   00_0011_1www_www1   0_0000_111w_www1
idxm      index,a   0000_100w_wwww_www0   00_0011_1www_www0   0_0000_111w_www0
igoto     word      0000_011w_wwww_www0
inc       M         0110_100m_mmmm_mmmm   01_0010_0mmm_mmmm   0_1001_00mm_mmmm
izsn      a         0000_0000_0001_0010   00_0000_0110_0010   0_0000_0001_0010
izsn      M         0110_010m_mmmm_mmmm   01_0001_0mmm_mmmm   0_1000_10mm_mmmm
ldspth                                    00_0000_0000_0111
ldsptl                                    00_0000_0000_0110
ldt16     word      0000_001w_wwww_www1   00_0011_0www_www1   0_0000_110w_www1
ldtabh    word      0000_101w_wwww_www1
ldtabl    word      0000_101w_wwww_www0
mov       a,I       0001_1111_kkkk_kkkk   10_1111_kkkk_kkkk   1_0111_kkkk_kkkk
mov       a,IO      0000_0000_11pp_pppp   00_0001_11pp_pppp   0_0000_101p_pppp
mov       a,M       0101_111m_mmmm_mmmm   00_1111_1mmm_mmmm   0_0111_11mm_mmmm
mov       IO,a      0000_0000_10pp_pppp   00_0001_10pp_pppp   0_0000_100p_pppp
mov       M,a       0101_110m_mmmm_mmmm   00_1011_1mmm_mmmm   0_0101_11mm_mmmm
mul                 0000_0000_0011_1100   00_0000_0111_1100
nadd      a,M       0011_011m_mmmm_mmmm   00_0111_0mmm_mmmm
nadd      M,a       0011_010m_mmmm_mmmm   00_0111_1mmm_mmmm
neg       a         0000_0000_0001_1001   00_0000_0110_1001   0_0000_0001_1001
neg       M         0111_001m_mmmm_mmmm   01_0100_1mmm_mmmm   0_1010_01mm_mmmm
nmov      a,M       0011_001m_mmmm_mmmm
nmov      M,a       0011_000m_mmmm_mmmm
nop                 0000_0000_0000_0000   00_0000_0000_0000   0_0000_0000_0000
not       a         0000_0000_0001_1000   00_0000_0110_1000   0_0000_0001_1000
not       M         0111_000m_mmmm_mmmm   01_0100_0mmm_mmmm   0_1010_00mm_mmmm
or        a,I       0001_1101_kkkk_kkkk   10_1101_kkkk_kkkk   1_0101_kkkk_kkkk
or        a,M       0101_011m_mmmm_mmmm   00_1110_1mmm_mmmm   0_0111_01mm_mmmm
or        M,a       0101_010m_mmmm_mmmm   00_1010_1mmm_mmmm   0_0101_01mm_mmmm
pcadd     a         0000_0000_0001_0111   00_0000_0110_0111   0_0000_0001_0111
pmode     n         0000_0000_010k_kkkk
popaf               0000_0000_0011_0011   00_0000_0111_0011   0_0000_0011_0011
popw      pcN       0000_0000_0110_tttt
popw      word      0000_010w_wwww_www0
pushaf              0000_0000_0011_0010   00_0000_0111_0010   0_0000_0011_0010
pushw     pcN       0000_0000_0111_tttt
pushw     word      0000_010w_wwww_www1
reset               0000_0000_0011_0101   00_0000_0111_0101   0_0000_0011_0101
ret                 0000_0000_0011_1010   00_0000_0111_1010   0_0000_0011_1010
ret       I         0000_1111_kkkk_kkkk   00_0010_kkkk_kkkk   0_0001_kkkk_kkkk
reti                0000_0000_0011_1011   00_0000_0111_1011   0_0000_0011_1011
set0      IO.n      0010_010b_bbpp_pppp   01_110b_bbpp_pppp   0_1110_bbbp_pppp
set0      M.n       1010_bbbm_mmmm_mmmm   10_010b_bbmm_mmmm   0_0011_bbb0_mmmm
set1      IO.n      0010_011b_bbpp_pppp   01_111b_bbpp_pppp   0_1111_bbbp_pppp
set1      M.n       1011_bbbm_mmmm_mmmm   10_011b_bbmm_mmmm   0_0011_bbb1_mmmm
sl        a         0000_0000_0001_1011   00_0000_0110_1011   0_0000_0001_1011
sl        M         0111_011m_mmmm_mmmm   01_0101_1mmm_mmmm   0_1010_11mm_mmmm
slc       a         0000_0000_0001_1101   00_0000_0110_1101   0_0000_0001_1101
slc       M         0111_101m_mmmm_mmmm   01_0110_1mmm_mmmm   0_1011_01mm_mmmm
sr        a         0000_0000_0001_1010   00_0000_0110_1010   0_0000_0001_1010
sr        M         0111_010m_mmmm_mmmm   01_0101_0mmm_mmmm   0_1010_10mm_mmmm
src       a         0000_0000_0001_1100   00_0000_0110_1100   0_0000_0001_1100
src       M         0111_100m_mmmm_mmmm   01_0110_0mmm_mmmm   0_1011_00mm_mmmm
stopexe             0000_0000_0011_0111   00_0000_0111_0111   0_0000_0011_0111
stopsys             0000_0000_0011_0110   00_0000_0111_0110   0_0000_0011_0110
stt16     word      0000_001w_wwww_www0   00_0011_0www_www0   0_0000_110w_www0
sub       a,I       0001_1001_kkkk_kkkk   10_1001_kkkk_kkkk   1_0001_kkkk_kkkk
sub       a,M       0100_011m_mmmm_mmmm   00_1100_1mmm_mmmm   0_0110_01mm_mmmm
sub       M,a       0100_010m_mmmm_mmmm   00_1000_1mmm_mmmm   0_0100_01mm_mmmm
subc      a         0000_0000_0001_0001   00_0000_0110_0001   0_0000_0001_0001
subc      a,M       0100_111m_mmmm_mmmm   00_1101_1mmm_mmmm   0_0110_11mm_mmmm
subc      M         0110_001m_mmmm_mmmm   01_0000_1mmm_mmmm   0_1000_01mm_mmmm
subc      M,a       0100_110m_mmmm_mmmm   00_1001_1mmm_mmmm   0_0100_11mm_mmmm
swap      a         0000_0000_0001_1110   00_0000_0110_1110   0_0000_0001_1110
swap      M         0111_110m_mmmm_mmmm
swapc     IO.n      0010_111b_bbpp_pppp   00_010b_bbpp_pppp
t0sn      IO.n      0010_000b_bbpp_pppp   01_100b_bbpp_pppp   0_1100_bbbp_pppp
t0sn      M.n       1000_bbbm_mmmm_mmmm   10_000b_bbmm_mmmm   0_0010_bbb0_mmmm
t1sn      IO.n      0010_001b_bbpp_pppp   01_101b_bbpp_pppp   0_1101_bbbp_pppp
t1sn      M.n       1001_bbbm_mmmm_mmmm   10_001b_bbmm_mmmm   0_0010_bbb1_mmmm
tog       IO.n      0010_100b_bbpp_pppp
wait0     IO.n      0010_101b_bbpp_pppp
wait1     IO.n      0010_110b_bbpp_pppp
wdreset             0000_0000_0011_0000   00_0000_0111_0000   0_0000_0011_0000
xch       M         0110_111m_mmmm_mmmm   01_0011_1mmm_mmmm   0_1001_11mm_mmmm
xor       a,I       0001_1110_kkkk_kkkk   10_1110_kkkk_kkkk   1_0110_kkkk_kkkk
xor       a,IO      0001_0000_01pp_pppp
xor       a,M       0101_101m_mmmm_mmmm   00_1111_0mmm_mmmm   0_0111_10mm_mmmm
xor       IO,a      0001_0000_00pp_pppp   00_0000_11pp_pppp   0_0000_011p_pppp
xor       M,a       0101_100m_mmmm_mmmm   00_1011_0mmm_mmmm   0_0101_10mm_mmmm

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 27, 2018, 07:18:11 pm
Thanks for the code. I seem to have an endianess problem somewhere.
I am using linux, but the IDE doesnt work with wine.
So I used windows to make and convert the file. Somehow bytes got swapped  :palm:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 27, 2018, 07:49:57 pm
[…]
If I counted correctly there are only these instruction set families
.Assembly   ASM_INSTR   SYM_83A
.Assembly   ASM_INSTR   SYM_84B
.Assembly   ASM_INSTR   SYM_85A
.Assembly   ASM_INSTR   SYM_86B
.Assembly   ICE_INSTR   SYM_83A
.Assembly   ICE_INSTR   SYM_86A
.Assembly   INSTRUMENT   SYM_82A
.Assembly   INSTRUMENT   SYM_83A
.Assembly   INSTRUMENT   SYM_86A

I suspect that INSTRUMENT means same for ASM and ICE

I had noticed those SYM_ whatever things in the files before, but didn't see their relation to the instruction sets. ASM_INSTR SYM_85A is found in files for devices both with (e.g. PMS130) and without (e.g. PFS154) the mul instruction. ASM_INSTR SYM_83A is found in files for devices with pushw (e.g. PMC884) without pushw (e.g. PMS232).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: westfw on November 28, 2018, 09:04:54 am
(Wow.   I just want to throw in a compliment.  This has been REALLY IMPRESSIVE!  Great work; excellent collaboration!)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on November 28, 2018, 08:47:40 pm
Maybe the Symbol Files have to be seen in conjuction with the inc files.
SYM_85A does not include the mul instruction.
The inc file for the pfs154 doesnt have anything related to mul and the ide complains that "mul not be supported at pfs154"

The inc file for the pms130 does have to registers defined
   MULOP      IO_RW      0x08
   MULRH      IO_RO      0x09
for the multiplication.

I couldnt find the device ids in the symbol files so that must be stored somewhere else.

So I guess the symbol files are templates for the ide that then get modified for the specific ic.

Edit: if I change the SYM in the INC file, instructions missing in the other family are no longer recognized. (syntax error)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 30, 2018, 12:21:26 pm
For all the people interested in ordering PADAUK parts and tools.

I ordered some stuff from lcsc.com with standard shipping. Payment was done using Paypal, delivery cost was around 7 USD. After 15 days my order arrived without any problems (direct shipping from China to my place).


Here is a list of ICs and tools from PADAUK I use.

Please consider to use the AFFILIATE LINKS from below when you order from lcsc.com (https://lcsc.com/search?q=padauk%20tech&promote=ZTU4NGt1MWVFOGtHWHZoVDZDYkZaS2xvMGtuMUlhNDBJMHJtb2xqK3VnbWRMYy84NDFQTjVkSGZ3N3ZmdEJodlo1bUtRUlpBMXhTaFl2alpLOVhEVVd6cGQ5NlltQ1lQU3l5YWpnR3ZDZUNkb1k1Vll3TGYwK2pRa1djMlZuY2phc2lu). This will give me some credits there and I can order more PADAUK parts to investigate.

THANK YOU!

---

ICs I use:

Flash based ICs (1000 erase/write cycles possible):
PFS154-S08 (https://lcsc.com/product-detail/Others_PADAUK-Tech-PFS154-S08_C317611.html?promote=NTBjZlBvSU9aWWlET0VCVkUrUGcrU1c0TkQ4NFBPcGlGZVExb1YvbFQ1UHlsWDhUTXlEaUZwc0xoSTc4YjJoOTZnTkdzUlVZTDZPY3VpeHhTUVNNQnJqZnRqMVNhNWN6a1NiSEFXTk81S0VWWkpyT2VOYlh5MitWSzVydmMwMjZJelFG)  (14 bit opcodes)
PFS154-S14 (https://lcsc.com/product-detail/Others_PADAUK-Tech-PFS154-S14_C317612.html?promote=ZWJiY2cvQk1Qb2xBS2RxRXZiQXlTcnN2amd6NHBaVmEzTGdHSGkzOHpHQjc2ck84TDMzWlVCR1M1cGpSWjBhdmcxNHh3OWxUMGQ2RFVXaWQvOFR0bERjcmxwNFN6V3VPNzVneFM0Y3RHZnBvZzkvMksvYUdKNlVwZjJqRVd0M1RYMFNN) (14 bit opcodes)

OTP ICs (One Time Programmable):
PMS154B-S14 (https://lcsc.com/product-detail/PADAUK_PADAUK-Tech-PMS154B_C129128.html?promote=MmVkYTcyVnU0YzNSRnNVRTRFbWNLWlp0MzdZNzJBdG5zeUVxaWNCREdtQzlsTjJMRS9KeXFWZGtvd1RQTXZOcGdOTktXN0ZjaFB2alBLU0FGYkhwOTYwYU9Bc09vaEdJckJUMkgwVGtDZnc1bnFaYVVBS1Z4WFBPSmZhRXorU2YwQytw) (14 bit opcodes)
PMS150C-S08 (https://lcsc.com/product-detail/PADAUK_PADAUK-Tech-PMS150C_C129127.html?promote=Nzc2YmJ1OGlseDIvMU02L29EN3I4ZlhUSDA4UjNBbEdHOEhWUVl6MHVORFc5Y20rUUZLWlNtUGVncndQVGxWRjZONzBQOXpadVZJSXB5dlg0cTBoMmNSVHc1amFBajhwTDN1WTNPRXROa0tiZVVYTE0rTkVxMDJTdU9wWXZub25xdjZS) (13 bit opcodes)

---

My Programmer: PDK 3S-P-002 (https://lcsc.com/product-detail/_PADAUK-Tech-PDK-3S-P-002_C248471.html?promote=YWIwY2NZV0FJeU9lMGQwWG1EaUsrQXdHTXU1UDF5YnRMdXJtbkgxa1JGS2kxYWZTU1UvemdLYTQ3elhJck04ckpwUWVRdWhmMXgyVGdEZHJvOTFXejZ3WGhTUGVUTE9oenNTSzRQZHZtOXBVWkc5VEVwdDM3elpUbzM0N1ZXZXoxcTdz) !!!OLD VERSION, DOES NOT SUPPORT PFS154 Flash based IC!!!!

Alternative Programmer: PDK 5S-P-003 (https://lcsc.com/product-detail/Development-Kits-Emulators-Simulators_PADAUK-Tech-5S-P-003_C263009.html?promote=NTQ0MUpsUisxei96ZG1QWnk3dEpKTDhCNjR4dldHaEhLY2g3ZVRkK1RGTU0zNVpmdlJ2d0NhY2hPWTAzUVlxNTlHRkhXZ21oYzVENU1uUHRsS016c2V2NWN1N2JjK2lYQ2tFN3hXUmYvcmlZV0FsZ1VGMDVYcy8rTDZWblVaOWQ1cWZS)

My ICE: PDK 5S-I-S01 (https://lcsc.com/product-detail/Development-Kits-Emulators-Simulators_PADAUK-Tech-PDK-5S-I-S01_C194849.html?promote=ZjU3ZFVTT2c0Rk1MUitrTWNjV09EeHN2bnBTVXBsUDRGUCt3V2lZdnhoZWVuenhQdGNpK21FQ3FOaFdNODRyV3FiZTkyVG44b2FrN0xSTHI1WjZod2FzQmltRm1NQVZMRlV1VVRzYmpTZFpPdFBwWEZEb3k4QUVyZEx4SWxhV0pKbEN3) !!! SUPPORTS ALL SINGLE CORE VARIANTS!!!

Alternative ICE: PDK 3S-I-003 (https://lcsc.com/product-detail/Development-Kits-Emulators-Simulators_PADAUK-Tech-PDK-3S-I-003_C341193.html?promote=NTVjNHFIZ0VuYUk4eXpXZ1BPS0RaRHdlL2V4SmNseEtVVElxZXo4bElmNDJaMlFNbGpVd254ZE8vTGZJOGZhTHNRYXh6ME1McnlNNlVoVWRWTlI4b3MrbEtRRTlReVo4eU9MVHRvOUNTYm5uMlZZN3ZSbHUrYVoxTjdLOThieXFndDV4) !!!OLD PRODUCT, ONLY FOR SOME MULTICORE VARIANTS!!!

---

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 30, 2018, 03:56:21 pm
Do we have any idea if the Padauk Programmer supports on-target debugging in any way?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 30, 2018, 04:49:27 pm
Do we have any idea if the Padauk Programmer supports on-target debugging in any way?

Philipp

Hi,

the programmer is just for writing to the IC. Usually the IDE inserts some "INIT-CODE" for IC testing and calibrating clock. This init code steals some valuable code space. It uses bit bang protocol on 3 IO pins to communicate with WRITER.

-> WRITER can not debug anything from your user program.
-> PADAUK CPU do not have any debug features (e.g. breakpoints) built in

Your best choice is to use the ICE. Then you get breakpoints and memory inspection from the IDE directly.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 01, 2018, 12:51:12 am
Disassembler for all Padauk MCUs.

Usage: pdisasm pdk [io_symbols [mem_symbols]]

To show instruction set: pdisasm 13 | 14 | 16 | all
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 01, 2018, 10:32:01 am
Disassembler for all Padauk MCUs.

Usage: pdisasm pdk [io_symbols [mem_symbols]]

To show instruction set: pdisasm 13 | 14 | 16 | all


Great job!
I've modified it so that it compiles under linux (none of those ms dependencies any more and a Makefile), hope thats ok (+ some whitespace changes)
You can look at the attached patch files to see what I did.
just 'make' it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 01, 2018, 12:35:31 pm
I've modified main so that it will load the io symbols automagically, because that was irritating me to no end ;)

Code: [Select]
--- original/padauk_disasm.cpp 2018-12-01 11:25:20.595205297 +0100
+++ padauk_disasm.cpp 2018-12-01 13:31:07.148535905 +0100
@@ -1,11 +1,11 @@
-
-#include "stdafx.h"
+#include <string.h>
+#include <stdlib.h>
 #include "pdk.h"
 #include "disasm.h"
 
 
-int main(int argc, char **argv)
-{
+int
+main(int argc, char **argv) {
  if (argc < 2) {
  printf("Usage: pdisasm pdk [ io_symbols [ mem_symbols] ]\n");
  return 0;
@@ -30,10 +30,17 @@
  auto d = CPadaukDisasm::New(pdk.bits);
  if (!d) { printf("Unsupported core (%i bits)\n", pdk.bits);  return -2; }
 
- if (argc > 2) d->io_symbols.ReadFile(argv[2]);
+ if (argc > 2) {
+ d->io_symbols.ReadFile(argv[2]);
+ } else {
+ char fname[17] = {};
+ sprintf(fname, "sym_io_%d.txt", pdk.bits);
+ d->io_symbols.ReadFile(fname);
+ }
+
  if (argc > 3) d->mem_symbols.ReadFile(argv[3]);
 
  d->disasm(pdk);
  }
-    return 0;
+ return 0;
 }
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 01, 2018, 12:57:14 pm
Here is the precompiled ready to run binary and support files for linux. I use Ubuntu 18.04 LTS so should be fine for any current distribution ( I hope ;)

small_possum is the same but with debug symbols stripped so its only about 45k in size ready to run.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 02, 2018, 04:40:25 pm
Today, I made a first step to inefficently compiling a small subset of C to Padauk asm code. The current version is very restricted and generates very inefficient code; it is untested.

There is no assembler / linker support, so the resulting .asm file has to be assembled in other ways.

Particularly noticeable restrictions:

* The only data types supported are the basic integer types. No pointers, arrays, struct, union, float, etc.
* Functions cannot have parameters.
* Functions can return at most 1 byte (i.e. only void, bool, char, signed char, unsigned char are allowed).
* Bitwise operations and shifts are no supported.
* Multiplicative operators are not supported.
* Functions are not reentrant.

Code in svn at https://svn.code.sf.net/p/sdcc/code/branches/pdk/sdcc, use -mpdk14 to target Padauk (despite the name, the set of instructions emitted is part of the common subset of the Padauk instruction sets).

Philipp

P.S.: The only allowed comparisons are for equality, i.e. == and !=, while <,<=, >, >= don't work. Fortunately, most attempts to use non-supported functionality result in compile-time errors.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 03, 2018, 08:44:39 am
I have a startup file for the pfs154 that doesnt dissasemble correctly using the current sets, I suspect that 85A is still different from the others

Has this been resolved? Do we know if there are encoding differences within the individual 13-Bit / 14-Bit / 16_ Bit instruction sets (apart from differences in the supported subset of instructions)?

In particular: Can we be reasonably sure that the 14-Bit instruction set at https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html reflects the actual encoding for the PFS154?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 03, 2018, 12:53:43 pm
I have a startup file for the pfs154 that doesnt dissasemble correctly using the current sets, I suspect that 85A is still different from the others

Has this been resolved? Do we know if there are encoding differences within the individual 13-Bit / 14-Bit / 16_ Bit instruction sets (apart from differences in the supported subset of instructions)?

In particular: Can we be reasonably sure that the 14-Bit instruction set at https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html reflects the actual encoding for the PFS154?

Philipp


Just checked again. Yes.
Startup code for the PFS154 (dissassembled with opossum on linux):

Code: [Select]
PDK version: 20
PDK data size:  2048 words
Free data size: 2016 words
MCU: PFS154 [ID: 0x2AA1]
Compiler version: 0.83B17
14 bit core
0000  0070  wdreset   
0001  2F00  mov       a, 0x00
0002  0182  mov       SP, a
0003  3FED  call      0x07ED
0004  018B  mov       IHRCR, a
0005  3FEE  call      0x07EE
0006  019A  mov       BGTR, a
0007  2F20  mov       a, 0x20
0008  019B  mov       MISC_LVR, a
0009  2F34  mov       a, 0x34
000A  0183  mov       CLKCMD, a
000B  3FFE  call      0x07FE
000C  2AFF  ceqsn     a, 0xFF
000D  3054  goto      0x0054
000E  3FED  call      0x07ED
000F  0B81  mov       M1, a
0010  1F91  set1      PAC.6
0011  2F20  mov       a, 0x20
0012  0B80  mov       M0, a
0013  1AD0  t1sn      PA.3
0014  3013  goto      0x0013
0015  1F90  set1      PA.6
0016  0063  dzsn      a
0017  3016  goto      0x0016
0018  1180  dzsn      M0
0019  3016  goto      0x0016
001A  1D90  set0      PA.6
001B  18D0  t0sn      PA.3
001C  301B  goto      0x001B
001D  2F01  mov       a, 0x01
001E  1950  t0sn      PA.5
001F  2FFF  mov       a, 0xFF
0020  0C01  add       a, M1
0021  018B  mov       IHRCR, a
0022  0B81  mov       M1, a
0023  1AD0  t1sn      PA.3
0024  3023  goto      0x0023
0025  1B50  t1sn      PA.5
0026  304F  goto      0x004F
0027  2F04  mov       a, 0x04
0028  0188  mov       MISC, a
0029  18D0  t0sn      PA.3
002A  3029  goto      0x0029
002B  2F02  mov       a, 0x02
002C  0182  mov       SP, a
002D  1304  clear     M4
002E  1305  clear     M5
002F  2F5E  mov       a, 0x5E
0030  0B82  mov       M2, a
0031  2F00  mov       a, 0x00
0032  0B83  mov       M3, a
0033  0006  ldsptl   
0034  0B04  xor       M4, a
0035  0007  ldspth   
0036  0805  add       M5, a
0037  1584  sl        M4
0038  1685  slc       M5
0039  1004  addc      M4
003A  1282  dec       M2
003B  1083  subc      M3
003C  1A40  t1sn      FLAG.C
003D  3033  goto      0x0033
003E  1F90  set1      PA.6
003F  1AD0  t1sn      PA.3
0040  303F  goto      0x003F
0041  1584  sl        M4
0042  1685  slc       M5
0043  0590  swapc     PA.6
0044  18D0  t0sn      PA.3
0045  3044  goto      0x0044
0046  1950  t0sn      PA.5
0047  303F  goto      0x003F
0048  1D90  set0      PA.6
0049  1AD0  t1sn      PA.3
004A  3049  goto      0x0049
004B  18D0  t0sn      PA.3
004C  304B  goto      0x004B
004D  1B50  t1sn      PA.5
004E  302B  goto      0x002B
004F  18D0  t0sn      PA.3
0050  304F  goto      0x004F
0051  1B50  t1sn      PA.5
0052  3011  goto      0x0011
0053  3053  goto      0x0053
0054  018B  mov       IHRCR, a
0055  0000  nop       // here a nop/wdreset pattern starts so that I can recognize my code
0056  0070  wdreset   
0057  0000  nop       
0058  0070  wdreset   
0059  0000  nop       
005A  0070  wdreset   
005B  0000  nop       
005C  0070  wdreset   
005D  0000  nop       
005E  3055  goto      0x0055 
....    // all other locations are 3FFF
07EF  1FFE  set1      GPCC.7
07F0  3FFF  call      0x07FF
07F1  3FFF  call      0x07FF
07F2  3FFF  call      0x07FF
07F3  3FFF  call      0x07FF
07F4  3FFF  call      0x07FF
07F5  3FFF  call      0x07FF
07F6  3FFF  call      0x07FF
07F7  3FFF  call      0x07FF
07F8  0000  nop       
07F9  0000  nop       
07FA  3FFF  call      0x07FF
07FB  3FFF  call      0x07FF
07FC  3FFF  call      0x07FF
07FD  3FFF  call      0x07FF
07FE  3FFF  call      0x07FF
07FF  3DFD  call      0x05FD

Edit: It's actually slightly different from the one posted above, but only single instructions and coherent with the encoding.
Probably the options I chose?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 03, 2018, 01:19:38 pm
I think the only family missing is for these chips:

grep -Rlsi SYM_86B

PMS134.INC
MCU371.INC
PMS132K.INC
PMS133.INC
PFS173.INC

---

The differences I can spot are minimal: 86B also includes the NMOV instruction but lacks the (explicit?) description of LDSPTL/LDSPTH but instead has LDTABL/LDTABH.
Also the order of the instructions in the symbol file is slightly different.

The datasheet claims that the pfs173 has 89 instructions (I count 88) while the pfs154 has 82.

The actual devices are thus slightly different: the PFS154 misses the NADD and COMP instructions as per datasheet. Dont know if the IDE will accept them anyway. And LDSPTL/LDSPTH is in the Symbol file but not documented.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 03, 2018, 02:05:20 pm
And trying to dissassemble the PFS173 startup code we get this:

PDK version: 20
PDK data size:  3072 words
Free data size: 3040 words
MCU: PFS173 [ID: 0x2AA2]
Compiler version: 0.83B17
15 bit core
Unsupported core (15 bits)

So I was almost right: there is a different encoding (but not for the pfs154) :-DD
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 03, 2018, 02:15:02 pm
So the 15-Bit encoding actually exists. Interesting. I hope it gets documented, too.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 03, 2018, 03:00:07 pm
Just noticed a small error I made in the linux sources that cuts off the first three bits of the printed opcode.
Corrected source below (also includes startupcode for pfs154 and 173) and precompiled binary.

Just a reminder to myself:
the amount of addressable memory is (core size in bits - 3)
16 -> 13 -> 8192 words, Family 83A
15 -> 12 -> 4096 words, Family 86B
14 -> 11 -> 2048 words, Family 85A
13 -> 10 -> 1024 words, Family 84B
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 03, 2018, 03:16:20 pm
15 bit instruction set confirmed. I thought it existed but the chips with 4 kW memory used the 16 bit instruction set, so I stopped looking.
Working on complete decode and updated disassembler.

Code: [Select]
6000   goto  0x0000
6FFF   goto  0x0FFF
7000   call  0x0000
7FFF   call  0x0FFF

12 bit program address
Probably 8 bit memory address.
IO address TBD.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 03, 2018, 07:17:57 pm
Today, I made a first step to inefficently compiling a small subset of C to Padauk asm code. The current version is very restricted and generates very inefficient code; it is untested.

There is no assembler / linker support, so the resulting .asm file has to be assembled in other ways.

[…]

Code in svn at https://svn.code.sf.net/p/sdcc/code/branches/pdk/sdcc, use -mpdk14 to target Padauk (despite the name, the set of instructions emitted is part of the common subset of the Padauk instruction sets).

On the second day, wrt. completeness of implementation of the C standard, this has now far surpassed Mini-C.

Noticeable remaining restrictions:

* Variables can only reside in RAM, not in code space
* Global and static variables are not initialized.
* No floating-point or bit-fields.
* Functions can return at most 2 bytes (i.e. no long or long long).
* Multiplicative operators are not supported.
* Functions are not reentrant.
* No support for variable arguments.
* No standard library.
* struct / union cannot be assigned, passed as arguments or returned.
* No compoundliterals.
* No access to I/O from C.

There is no glue to connect this to assembler / linker yet, so the only useable output is asm code.
The generated asm code is still very inefficient. I will look into improving that a bit soon.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 03, 2018, 07:27:53 pm
Has this been resolved? Do we know if there are encoding differences within the individual 13-Bit / 14-Bit / 16_ Bit instruction sets (apart from differences in the supported subset of instructions)?
In particular: Can we be reasonably sure that the 14-Bit instruction set at https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html reflects the actual encoding for the PFS154?

Philipp

I updated the instruction set pages (13,14,16 bit) with all known stuff gathered from the contributors of this forum:

https://free-pdk.github.io/

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 03, 2018, 07:43:54 pm
15 bit instruction set

Used by PMS132K, PMS133, PMS134, PFS173, MCU371

Code: [Select]
0x0000  000_0000_0000_0000  nop
0x0001  000_0000_0000_0001
0x0002  000_0000_0000_001-
0x0004  000_0000_0000_01--
0x0008  000_0000_0000_1---
0x0010  000_0000_0001_----
0x0020  000_0000_001-_----
0x0040  000_0000_010-_----
0x0050  000_0000_0101_----
0x0060  000_0000_0110_0000  addc     a
0x0061  000_0000_0110_0001  subc     a
0x0062  000_0000_0110_0010  izsn     a
0x0063  000_0000_0110_0011  dzsn     a
0x0064  000_0000_0110_0100
0x0065  000_0000_0110_0101
0x0066  000_0000_0110_0110
0x0067  000_0000_0110_0111  pcadd    a
0x0068  000_0000_0110_1000  not      a
0x0069  000_0000_0110_1001  neg      a
0x006A  000_0000_0110_1010  sr       a
0x006B  000_0000_0110_1011  sl       a
0x006C  000_0000_0110_1100  src      a
0x006D  000_0000_0110_1101  slc      a
0x006E  000_0000_0110_1110  swap     a
0x006F  000_0000_0110_1111
0x0070  000_0000_0111_0000  wdreset
0x0071  000_0000_0111_0001
0x0072  000_0000_0111_0010  pushaf
0x0073  000_0000_0111_0011  popaf
0x0074  000_0000_0111_0100
0x0075  000_0000_0111_0101  reset
0x0076  000_0000_0111_0110  stopsys
0x0077  000_0000_0111_0111  stopexe
0x0078  000_0000_0111_1000  engint
0x0079  000_0000_0111_1001  disgint
0x007A  000_0000_0111_1010  ret
0x007B  000_0000_0111_1011  reti
0x007C  000_0000_0111_1100  mul
0x007D  000_0000_0111_1101
0x007E  000_0000_0111_1110
0x007F  000_0000_0111_1110
0x0080  000_0000_1ppp_pppp  xor      a,IO
0x0100  000_0001_0ppp_pppp  mov      IO,a
0x0180  000_0001_1ppp_pppp  mov      a,IO
0x0200  000_0010_kkkk_kkkk  ret      I
0x0300  000_0011_----_----
0x0400  000_0100_----_----
0x0500  000_0101_wwww_www0  ldtabl   word
0x0501  000_0101_wwww_www1  ldtabh   word
0x0600  000_0110_wwww_www0  stt16    word
0x0601  000_0110_wwww_www1  ldt16    word
0x0700  000_0111_wwww_www0  idxm     index,a
0x0701  000_0111_wwww_www1  idxm     a,index
0x0800  000_10--_----_----
0x0C00  000_1100_mmmm_mmmm  comp     a,M
0x0D00  000_1101_mmmm_mmmm  comp     M,a
0x0E00  000_1110_mmmm_mmmm  nadd     a,M
0x0F00  000_1111_mmmm_mmmm  nadd     M,a
0x1000  001_0000_mmmm_mmmm  add      M,a
0x1100  001_0001_mmmm_mmmm  sub      M,a
0x1200  001_0010_mmmm_mmmm  addc     M,a
0x1300  001_0011_mmmm_mmmm  subc     M,a
0x1400  001_0100_mmmm_mmmm  and      M,a
0x1500  001_0101_mmmm_mmmm  or       M,a
0x1600  001_0110_mmmm_mmmm  xor      M,a
0x1700  001_0111_mmmm_mmmm  mov      M,a
0x1800  001_1000_mmmm_mmmm  add      a,M
0x1900  001_1001_mmmm_mmmm  sub      a,M
0x1A00  001_1010_mmmm_mmmm  addc     a,M
0x1B00  001_1011_mmmm_mmmm  subc     a,M
0x1C00  001_1100_mmmm_mmmm  and      a,M
0x1D00  001_1101_mmmm_mmmm  or       a,M
0x1E00  001_1110_mmmm_mmmm  xor      a,M
0x1F00  001_1111_mmmm_mmmm  mov      a,M
0x2000  010_0000_mmmm_mmmm  addc     M
0x2100  010_0001_mmmm_mmmm  subc     M
0x2200  010_0010_mmmm_mmmm  izsn     M
0x2300  010_0011_mmmm_mmmm  dzsn     M
0x2400  010_0100_mmmm_mmmm  inc      M
0x2500  010_0101_mmmm_mmmm  dec      M
0x2600  010_0110_mmmm_mmmm  clear    M
0x2700  010_0111_mmmm_mmmm  xch      M
0x2800  010_1000_mmmm_mmmm  not      M
0x2900  010_1001_mmmm_mmmm  neg      M
0x2A00  010_1010_mmmm_mmmm  sr       M
0x2B00  010_1011_mmmm_mmmm  sl       M
0x2C00  010_1100_mmmm_mmmm  src      M
0x2D00  010_1101_mmmm_mmmm  slc      M
0x2E00  010_1110_mmmm_mmmm  ceqsn    a,M
0x2F00  010_1111_mmmm_mmmm  cneqsn   a,M
0x3000  011_00bb_bppp_pppp  t0sn     IO.n
0x3400  011_01bb_bppp_pppp  t1sn     IO.n
0x3800  011_10bb_bppp_pppp  set0     IO.n
0x3C00  011_11bb_bppp_pppp  set1     IO.n
0x4000  100_00bb_bmmm_mmmm  t0sn     M.n
0x4400  100_01bb_bmmm_mmmm  t1sn     M.n
0x4800  100_10bb_bmmm_mmmm  set0     M.n
0x4C00  100_11bb_bmmm_mmmm  set1     M.n
0x5000  101_0000_kkkk_kkkk  add      a,I
0x5100  101_0001_kkkk_kkkk  sub      a,I
0x5200  101_0010_kkkk_kkkk  ceqsn    a,I
0x5300  101_0011_kkkk_kkkk  cneqsn   a,I
0x5400  101_0100_kkkk_kkkk  and      a,I
0x5500  101_0101_kkkk_kkkk  or       a,I
0x5600  101_0110_kkkk_kkkk  xor      a,I
0x5700  101_0111_kkkk_kkkk  mov      a,I
0x5800  101_10--_----_----
0x5C00  101_11bb_bppp_pppp  swapc    IO.n
0x6000  110_aaaa_aaaa_aaaa  goto     label
0x7000  111_aaaa_aaaa_aaaa  call     label

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 03, 2018, 08:00:00 pm
Edit: It's actually slightly different from the one posted above, but only single instructions and coherent with the encoding.
Probably the options I chose?

Yes, I think so. Different .ADJUST_IC options and different code size.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 03, 2018, 08:09:57 pm
Just a reminder to myself:
the amount of addressable memory is (core size in bits - 3)
16 -> 13 -> 8192 words, Family 83A
15 -> 12 -> 4096 words, Family 86B
14 -> 11 -> 2048 words, Family 85A
13 -> 10 -> 1024 words, Family 84B

Also...

16 -> 13 -> 8192 words, Family 82A  [PMC882 PDK22C13 PDK22C13A PDK22C58 PDK22C58A PDK82C12 PDK82C13 PDK82S_EV]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 03, 2018, 08:23:58 pm
16/15/14/13 bit instruction encoding sorted by 16 bit opcode
Code: [Select]
nop                 0000_0000_0000_0000   000_0000_0000_0000   00_0000_0000_0000   0_0000_0000_0000
ldsptl                                                         00_0000_0000_0110
ldspth                                                         00_0000_0000_0111
addc      a         0000_0000_0001_0000   000_0000_0110_0000   00_0000_0110_0000   0_0000_0001_0000
subc      a         0000_0000_0001_0001   000_0000_0110_0001   00_0000_0110_0001   0_0000_0001_0001
izsn      a         0000_0000_0001_0010   000_0000_0110_0010   00_0000_0110_0010   0_0000_0001_0010
dzsn      a         0000_0000_0001_0011   000_0000_0110_0011   00_0000_0110_0011   0_0000_0001_0011
pcadd     a         0000_0000_0001_0111   000_0000_0110_0111   00_0000_0110_0111   0_0000_0001_0111
not       a         0000_0000_0001_1000   000_0000_0110_1000   00_0000_0110_1000   0_0000_0001_1000
neg       a         0000_0000_0001_1001   000_0000_0110_1001   00_0000_0110_1001   0_0000_0001_1001
sr        a         0000_0000_0001_1010   000_0000_0110_1010   00_0000_0110_1010   0_0000_0001_1010
sl        a         0000_0000_0001_1011   000_0000_0110_1011   00_0000_0110_1011   0_0000_0001_1011
src       a         0000_0000_0001_1100   000_0000_0110_1100   00_0000_0110_1100   0_0000_0001_1100
slc       a         0000_0000_0001_1101   000_0000_0110_1101   00_0000_0110_1101   0_0000_0001_1101
swap      a         0000_0000_0001_1110   000_0000_0110_1110   00_0000_0110_1110   0_0000_0001_1110
delay     a         0000_0000_0001_1111
wdreset             0000_0000_0011_0000   000_0000_0111_0000   00_0000_0111_0000   0_0000_0011_0000
pushaf              0000_0000_0011_0010   000_0000_0111_0010   00_0000_0111_0010   0_0000_0011_0010
popaf               0000_0000_0011_0011   000_0000_0111_0011   00_0000_0111_0011   0_0000_0011_0011
reset               0000_0000_0011_0101   000_0000_0111_0101   00_0000_0111_0101   0_0000_0011_0101
stopsys             0000_0000_0011_0110   000_0000_0111_0110   00_0000_0111_0110   0_0000_0011_0110
stopexe             0000_0000_0011_0111   000_0000_0111_0111   00_0000_0111_0111   0_0000_0011_0111
engint              0000_0000_0011_1000   000_0000_0111_1000   00_0000_0111_1000   0_0000_0011_1000
disgint             0000_0000_0011_1001   000_0000_0111_1001   00_0000_0111_1001   0_0000_0011_1001
ret                 0000_0000_0011_1010   000_0000_0111_1010   00_0000_0111_1010   0_0000_0011_1010
reti                0000_0000_0011_1011   000_0000_0111_1011   00_0000_0111_1011   0_0000_0011_1011
mul                 0000_0000_0011_1100   000_0000_0111_1100   00_0000_0111_1100
pmode     n         0000_0000_010k_kkkk
popw      pcN       0000_0000_0110_tttt
pushw     pcN       0000_0000_0111_tttt
mov       IO,a      0000_0000_10pp_pppp   000_0001_0ppp_pppp   00_0001_10pp_pppp   0_0000_100p_pppp
mov       a,IO      0000_0000_11pp_pppp   000_0001_1ppp_pppp   00_0001_11pp_pppp   0_0000_101p_pppp
cneqsn    a,I       0000_0001_kkkk_kkkk   101_0011_kkkk_kkkk   10_1011_kkkk_kkkk   1_0011_kkkk_kkkk
stt16     word      0000_001w_wwww_www0   000_0110_wwww_www0   00_0011_0www_www0   0_0000_110w_www0
ldt16     word      0000_001w_wwww_www1   000_0110_wwww_www1   00_0011_0www_www1   0_0000_110w_www1
popw      word      0000_010w_wwww_www0
pushw     word      0000_010w_wwww_www1
igoto     word      0000_011w_wwww_www0
icall     word      0000_011w_wwww_www1
idxm      index,a   0000_100w_wwww_www0   000_0111_wwww_www0   00_0011_1www_www0   0_0000_111w_www0
idxm      a,index   0000_100w_wwww_www1   000_0111_wwww_www1   00_0011_1www_www1   0_0000_111w_www1
ldtabl    word      0000_101w_wwww_www0   000_0101_wwww_www0
ldtabh    word      0000_101w_wwww_www1   000_0101_wwww_www1
delay     I         0000_1110_kkkk_kkkk
ret       I         0000_1111_kkkk_kkkk   000_0010_kkkk_kkkk   00_0010_kkkk_kkkk   0_0001_kkkk_kkkk
xor       IO,a      0001_0000_00pp_pppp   000_0000_1ppp_pppp   00_0000_11pp_pppp   0_0000_011p_pppp
xor       a,IO      0001_0000_01pp_pppp
cneqsn    M,a       0001_010m_mmmm_mmmm
cneqsn    a,M       0001_011m_mmmm_mmmm   010_1111_mmmm_mmmm   01_0111_1mmm_mmmm   0_1011_11mm_mmmm
add       a,I       0001_1000_kkkk_kkkk   101_0000_kkkk_kkkk   10_1000_kkkk_kkkk   1_0000_kkkk_kkkk
sub       a,I       0001_1001_kkkk_kkkk   101_0001_kkkk_kkkk   10_1001_kkkk_kkkk   1_0001_kkkk_kkkk
ceqsn     a,I       0001_1010_kkkk_kkkk   101_0010_kkkk_kkkk   10_1010_kkkk_kkkk   1_0010_kkkk_kkkk
comp      a,I       0001_1011_kkkk_kkkk
and       a,I       0001_1100_kkkk_kkkk   101_0100_kkkk_kkkk   10_1100_kkkk_kkkk   1_0100_kkkk_kkkk
or        a,I       0001_1101_kkkk_kkkk   101_0101_kkkk_kkkk   10_1101_kkkk_kkkk   1_0101_kkkk_kkkk
xor       a,I       0001_1110_kkkk_kkkk   101_0110_kkkk_kkkk   10_1110_kkkk_kkkk   1_0110_kkkk_kkkk
mov       a,I       0001_1111_kkkk_kkkk   101_0111_kkkk_kkkk   10_1111_kkkk_kkkk   1_0111_kkkk_kkkk
t0sn      IO.n      0010_000b_bbpp_pppp   011_00bb_bppp_pppp   01_100b_bbpp_pppp   0_1100_bbbp_pppp
t1sn      IO.n      0010_001b_bbpp_pppp   011_01bb_bppp_pppp   01_101b_bbpp_pppp   0_1101_bbbp_pppp
set0      IO.n      0010_010b_bbpp_pppp   011_10bb_bppp_pppp   01_110b_bbpp_pppp   0_1110_bbbp_pppp
set1      IO.n      0010_011b_bbpp_pppp   011_11bb_bppp_pppp   01_111b_bbpp_pppp   0_1111_bbbp_pppp
tog       IO.n      0010_100b_bbpp_pppp
wait0     IO.n      0010_101b_bbpp_pppp
wait1     IO.n      0010_110b_bbpp_pppp
swapc     IO.n      0010_111b_bbpp_pppp   101_11bb_bppp_pppp   00_010b_bbpp_pppp
nmov      M,a       0011_000m_mmmm_mmmm
nmov      a,M       0011_001m_mmmm_mmmm
nadd      M,a       0011_010m_mmmm_mmmm   000_1111_mmmm_mmmm   00_0111_1mmm_mmmm
nadd      a,M       0011_011m_mmmm_mmmm   000_1110_mmmm_mmmm   00_0111_0mmm_mmmm
ceqsn     M,a       0011_100m_mmmm_mmmm
ceqsn     a,M       0011_101m_mmmm_mmmm   010_1110_mmmm_mmmm   01_0111_0mmm_mmmm   0_1011_10mm_mmmm
comp      M,a       0011_110m_mmmm_mmmm   000_1101_mmmm_mmmm   00_0110_1mmm_mmmm
comp      a,M       0011_111m_mmmm_mmmm   000_1100_mmmm_mmmm   00_0110_0mmm_mmmm
add       M,a       0100_000m_mmmm_mmmm   001_0000_mmmm_mmmm   00_1000_0mmm_mmmm   0_0100_00mm_mmmm
add       a,M       0100_001m_mmmm_mmmm   001_1000_mmmm_mmmm   00_1100_0mmm_mmmm   0_0110_00mm_mmmm
sub       M,a       0100_010m_mmmm_mmmm   001_0001_mmmm_mmmm   00_1000_1mmm_mmmm   0_0100_01mm_mmmm
sub       a,M       0100_011m_mmmm_mmmm   001_1001_mmmm_mmmm   00_1100_1mmm_mmmm   0_0110_01mm_mmmm
addc      M,a       0100_100m_mmmm_mmmm   001_0010_mmmm_mmmm   00_1001_0mmm_mmmm   0_0100_10mm_mmmm
addc      a,M       0100_101m_mmmm_mmmm   001_1010_mmmm_mmmm   00_1101_0mmm_mmmm   0_0110_10mm_mmmm
subc      M,a       0100_110m_mmmm_mmmm   001_0011_mmmm_mmmm   00_1001_1mmm_mmmm   0_0100_11mm_mmmm
subc      a,M       0100_111m_mmmm_mmmm   001_1011_mmmm_mmmm   00_1101_1mmm_mmmm   0_0110_11mm_mmmm
and       M,a       0101_000m_mmmm_mmmm   001_0100_mmmm_mmmm   00_1010_0mmm_mmmm   0_0101_00mm_mmmm
and       a,M       0101_001m_mmmm_mmmm   001_1100_mmmm_mmmm   00_1110_0mmm_mmmm   0_0111_00mm_mmmm
or        M,a       0101_010m_mmmm_mmmm   001_0101_mmmm_mmmm   00_1010_1mmm_mmmm   0_0101_01mm_mmmm
or        a,M       0101_011m_mmmm_mmmm   001_1101_mmmm_mmmm   00_1110_1mmm_mmmm   0_0111_01mm_mmmm
xor       M,a       0101_100m_mmmm_mmmm   001_0110_mmmm_mmmm   00_1011_0mmm_mmmm   0_0101_10mm_mmmm
xor       a,M       0101_101m_mmmm_mmmm   001_1110_mmmm_mmmm   00_1111_0mmm_mmmm   0_0111_10mm_mmmm
mov       M,a       0101_110m_mmmm_mmmm   001_0111_mmmm_mmmm   00_1011_1mmm_mmmm   0_0101_11mm_mmmm
mov       a,M       0101_111m_mmmm_mmmm   001_1111_mmmm_mmmm   00_1111_1mmm_mmmm   0_0111_11mm_mmmm
addc      M         0110_000m_mmmm_mmmm   010_0000_mmmm_mmmm   01_0000_0mmm_mmmm   0_1000_00mm_mmmm
subc      M         0110_001m_mmmm_mmmm   010_0001_mmmm_mmmm   01_0000_1mmm_mmmm   0_1000_01mm_mmmm
izsn      M         0110_010m_mmmm_mmmm   010_0010_mmmm_mmmm   01_0001_0mmm_mmmm   0_1000_10mm_mmmm
dzsn      M         0110_011m_mmmm_mmmm   010_0011_mmmm_mmmm   01_0001_1mmm_mmmm   0_1000_11mm_mmmm
inc       M         0110_100m_mmmm_mmmm   010_0100_mmmm_mmmm   01_0010_0mmm_mmmm   0_1001_00mm_mmmm
dec       M         0110_101m_mmmm_mmmm   010_0101_mmmm_mmmm   01_0010_1mmm_mmmm   0_1001_01mm_mmmm
clear     M         0110_110m_mmmm_mmmm   010_0110_mmmm_mmmm   01_0011_0mmm_mmmm   0_1001_10mm_mmmm
xch       M         0110_111m_mmmm_mmmm   010_0111_mmmm_mmmm   01_0011_1mmm_mmmm   0_1001_11mm_mmmm
not       M         0111_000m_mmmm_mmmm   010_1000_mmmm_mmmm   01_0100_0mmm_mmmm   0_1010_00mm_mmmm
neg       M         0111_001m_mmmm_mmmm   010_1001_mmmm_mmmm   01_0100_1mmm_mmmm   0_1010_01mm_mmmm
sr        M         0111_010m_mmmm_mmmm   010_1010_mmmm_mmmm   01_0101_0mmm_mmmm   0_1010_10mm_mmmm
sl        M         0111_011m_mmmm_mmmm   010_1011_mmmm_mmmm   01_0101_1mmm_mmmm   0_1010_11mm_mmmm
src       M         0111_100m_mmmm_mmmm   010_1100_mmmm_mmmm   01_0110_0mmm_mmmm   0_1011_00mm_mmmm
slc       M         0111_101m_mmmm_mmmm   010_1101_mmmm_mmmm   01_0110_1mmm_mmmm   0_1011_01mm_mmmm
swap      M         0111_110m_mmmm_mmmm
delay     M         0111_111m_mmmm_mmmm
t0sn      M.n       1000_bbbm_mmmm_mmmm   100_00bb_bmmm_mmmm   10_000b_bbmm_mmmm   0_0010_bbb0_mmmm
t1sn      M.n       1001_bbbm_mmmm_mmmm   100_01bb_bmmm_mmmm   10_001b_bbmm_mmmm   0_0010_bbb1_mmmm
set0      M.n       1010_bbbm_mmmm_mmmm   100_10bb_bmmm_mmmm   10_010b_bbmm_mmmm   0_0011_bbb0_mmmm
set1      M.n       1011_bbbm_mmmm_mmmm   100_11bb_bmmm_mmmm   10_011b_bbmm_mmmm   0_0011_bbb1_mmmm
goto      label     110a_aaaa_aaaa_aaaa   110_aaaa_aaaa_aaaa   11_0aaa_aaaa_aaaa   1_10aa_aaaa_aaaa
call      label     111a_aaaa_aaaa_aaaa   111_aaaa_aaaa_aaaa   11_1aaa_aaaa_aaaa   1_11aa_aaaa_aaaa


16/15/14/13 bit instruction encoding sorted by mnemonic
Code: [Select]
add       a,I       0001_1000_kkkk_kkkk   101_0000_kkkk_kkkk   10_1000_kkkk_kkkk   1_0000_kkkk_kkkk
add       a,M       0100_001m_mmmm_mmmm   001_1000_mmmm_mmmm   00_1100_0mmm_mmmm   0_0110_00mm_mmmm
add       M,a       0100_000m_mmmm_mmmm   001_0000_mmmm_mmmm   00_1000_0mmm_mmmm   0_0100_00mm_mmmm
addc      a         0000_0000_0001_0000   000_0000_0110_0000   00_0000_0110_0000   0_0000_0001_0000
addc      a,M       0100_101m_mmmm_mmmm   001_1010_mmmm_mmmm   00_1101_0mmm_mmmm   0_0110_10mm_mmmm
addc      M         0110_000m_mmmm_mmmm   010_0000_mmmm_mmmm   01_0000_0mmm_mmmm   0_1000_00mm_mmmm
addc      M,a       0100_100m_mmmm_mmmm   001_0010_mmmm_mmmm   00_1001_0mmm_mmmm   0_0100_10mm_mmmm
and       a,I       0001_1100_kkkk_kkkk   101_0100_kkkk_kkkk   10_1100_kkkk_kkkk   1_0100_kkkk_kkkk
and       a,M       0101_001m_mmmm_mmmm   001_1100_mmmm_mmmm   00_1110_0mmm_mmmm   0_0111_00mm_mmmm
and       M,a       0101_000m_mmmm_mmmm   001_0100_mmmm_mmmm   00_1010_0mmm_mmmm   0_0101_00mm_mmmm
call      label     111a_aaaa_aaaa_aaaa   111_aaaa_aaaa_aaaa   11_1aaa_aaaa_aaaa   1_11aa_aaaa_aaaa
ceqsn     a,I       0001_1010_kkkk_kkkk   101_0010_kkkk_kkkk   10_1010_kkkk_kkkk   1_0010_kkkk_kkkk
ceqsn     a,M       0011_101m_mmmm_mmmm   010_1110_mmmm_mmmm   01_0111_0mmm_mmmm   0_1011_10mm_mmmm
ceqsn     M,a       0011_100m_mmmm_mmmm
clear     M         0110_110m_mmmm_mmmm   010_0110_mmmm_mmmm   01_0011_0mmm_mmmm   0_1001_10mm_mmmm
cneqsn    a,I       0000_0001_kkkk_kkkk   101_0011_kkkk_kkkk   10_1011_kkkk_kkkk   1_0011_kkkk_kkkk
cneqsn    a,M       0001_011m_mmmm_mmmm   010_1111_mmmm_mmmm   01_0111_1mmm_mmmm   0_1011_11mm_mmmm
cneqsn    M,a       0001_010m_mmmm_mmmm
comp      a,I       0001_1011_kkkk_kkkk
comp      a,M       0011_111m_mmmm_mmmm   000_1100_mmmm_mmmm   00_0110_0mmm_mmmm
comp      M,a       0011_110m_mmmm_mmmm   000_1101_mmmm_mmmm   00_0110_1mmm_mmmm
dec       M         0110_101m_mmmm_mmmm   010_0101_mmmm_mmmm   01_0010_1mmm_mmmm   0_1001_01mm_mmmm
delay     a         0000_0000_0001_1111
delay     I         0000_1110_kkkk_kkkk
delay     M         0111_111m_mmmm_mmmm
disgint             0000_0000_0011_1001   000_0000_0111_1001   00_0000_0111_1001   0_0000_0011_1001
dzsn      a         0000_0000_0001_0011   000_0000_0110_0011   00_0000_0110_0011   0_0000_0001_0011
dzsn      M         0110_011m_mmmm_mmmm   010_0011_mmmm_mmmm   01_0001_1mmm_mmmm   0_1000_11mm_mmmm
engint              0000_0000_0011_1000   000_0000_0111_1000   00_0000_0111_1000   0_0000_0011_1000
goto      label     110a_aaaa_aaaa_aaaa   110_aaaa_aaaa_aaaa   11_0aaa_aaaa_aaaa   1_10aa_aaaa_aaaa
icall     word      0000_011w_wwww_www1
idxm      a,index   0000_100w_wwww_www1   000_0111_wwww_www1   00_0011_1www_www1   0_0000_111w_www1
idxm      index,a   0000_100w_wwww_www0   000_0111_wwww_www0   00_0011_1www_www0   0_0000_111w_www0
igoto     word      0000_011w_wwww_www0
inc       M         0110_100m_mmmm_mmmm   010_0100_mmmm_mmmm   01_0010_0mmm_mmmm   0_1001_00mm_mmmm
izsn      a         0000_0000_0001_0010   000_0000_0110_0010   00_0000_0110_0010   0_0000_0001_0010
izsn      M         0110_010m_mmmm_mmmm   010_0010_mmmm_mmmm   01_0001_0mmm_mmmm   0_1000_10mm_mmmm
ldspth                                                         00_0000_0000_0111
ldsptl                                                         00_0000_0000_0110
ldt16     word      0000_001w_wwww_www1   000_0110_wwww_www1   00_0011_0www_www1   0_0000_110w_www1
ldtabh    word      0000_101w_wwww_www1   000_0101_wwww_www1
ldtabl    word      0000_101w_wwww_www0   000_0101_wwww_www0
mov       a,I       0001_1111_kkkk_kkkk   101_0111_kkkk_kkkk   10_1111_kkkk_kkkk   1_0111_kkkk_kkkk
mov       a,IO      0000_0000_11pp_pppp   000_0001_1ppp_pppp   00_0001_11pp_pppp   0_0000_101p_pppp
mov       a,M       0101_111m_mmmm_mmmm   001_1111_mmmm_mmmm   00_1111_1mmm_mmmm   0_0111_11mm_mmmm
mov       IO,a      0000_0000_10pp_pppp   000_0001_0ppp_pppp   00_0001_10pp_pppp   0_0000_100p_pppp
mov       M,a       0101_110m_mmmm_mmmm   001_0111_mmmm_mmmm   00_1011_1mmm_mmmm   0_0101_11mm_mmmm
mul                 0000_0000_0011_1100   000_0000_0111_1100   00_0000_0111_1100
nadd      a,M       0011_011m_mmmm_mmmm   000_1110_mmmm_mmmm   00_0111_0mmm_mmmm
nadd      M,a       0011_010m_mmmm_mmmm   000_1111_mmmm_mmmm   00_0111_1mmm_mmmm
neg       a         0000_0000_0001_1001   000_0000_0110_1001   00_0000_0110_1001   0_0000_0001_1001
neg       M         0111_001m_mmmm_mmmm   010_1001_mmmm_mmmm   01_0100_1mmm_mmmm   0_1010_01mm_mmmm
nmov      a,M       0011_001m_mmmm_mmmm
nmov      M,a       0011_000m_mmmm_mmmm
nop                 0000_0000_0000_0000   000_0000_0000_0000   00_0000_0000_0000   0_0000_0000_0000
not       a         0000_0000_0001_1000   000_0000_0110_1000   00_0000_0110_1000   0_0000_0001_1000
not       M         0111_000m_mmmm_mmmm   010_1000_mmmm_mmmm   01_0100_0mmm_mmmm   0_1010_00mm_mmmm
or        a,I       0001_1101_kkkk_kkkk   101_0101_kkkk_kkkk   10_1101_kkkk_kkkk   1_0101_kkkk_kkkk
or        a,M       0101_011m_mmmm_mmmm   001_1101_mmmm_mmmm   00_1110_1mmm_mmmm   0_0111_01mm_mmmm
or        M,a       0101_010m_mmmm_mmmm   001_0101_mmmm_mmmm   00_1010_1mmm_mmmm   0_0101_01mm_mmmm
pcadd     a         0000_0000_0001_0111   000_0000_0110_0111   00_0000_0110_0111   0_0000_0001_0111
pmode     n         0000_0000_010k_kkkk
popaf               0000_0000_0011_0011   000_0000_0111_0011   00_0000_0111_0011   0_0000_0011_0011
popw      pcN       0000_0000_0110_tttt
popw      word      0000_010w_wwww_www0
pushaf              0000_0000_0011_0010   000_0000_0111_0010   00_0000_0111_0010   0_0000_0011_0010
pushw     pcN       0000_0000_0111_tttt
pushw     word      0000_010w_wwww_www1
reset               0000_0000_0011_0101   000_0000_0111_0101   00_0000_0111_0101   0_0000_0011_0101
ret                 0000_0000_0011_1010   000_0000_0111_1010   00_0000_0111_1010   0_0000_0011_1010
ret       I         0000_1111_kkkk_kkkk   000_0010_kkkk_kkkk   00_0010_kkkk_kkkk   0_0001_kkkk_kkkk
reti                0000_0000_0011_1011   000_0000_0111_1011   00_0000_0111_1011   0_0000_0011_1011
set0      IO.n      0010_010b_bbpp_pppp   011_10bb_bppp_pppp   01_110b_bbpp_pppp   0_1110_bbbp_pppp
set0      M.n       1010_bbbm_mmmm_mmmm   100_10bb_bmmm_mmmm   10_010b_bbmm_mmmm   0_0011_bbb0_mmmm
set1      IO.n      0010_011b_bbpp_pppp   011_11bb_bppp_pppp   01_111b_bbpp_pppp   0_1111_bbbp_pppp
set1      M.n       1011_bbbm_mmmm_mmmm   100_11bb_bmmm_mmmm   10_011b_bbmm_mmmm   0_0011_bbb1_mmmm
sl        a         0000_0000_0001_1011   000_0000_0110_1011   00_0000_0110_1011   0_0000_0001_1011
sl        M         0111_011m_mmmm_mmmm   010_1011_mmmm_mmmm   01_0101_1mmm_mmmm   0_1010_11mm_mmmm
slc       a         0000_0000_0001_1101   000_0000_0110_1101   00_0000_0110_1101   0_0000_0001_1101
slc       M         0111_101m_mmmm_mmmm   010_1101_mmmm_mmmm   01_0110_1mmm_mmmm   0_1011_01mm_mmmm
sr        a         0000_0000_0001_1010   000_0000_0110_1010   00_0000_0110_1010   0_0000_0001_1010
sr        M         0111_010m_mmmm_mmmm   010_1010_mmmm_mmmm   01_0101_0mmm_mmmm   0_1010_10mm_mmmm
src       a         0000_0000_0001_1100   000_0000_0110_1100   00_0000_0110_1100   0_0000_0001_1100
src       M         0111_100m_mmmm_mmmm   010_1100_mmmm_mmmm   01_0110_0mmm_mmmm   0_1011_00mm_mmmm
stopexe             0000_0000_0011_0111   000_0000_0111_0111   00_0000_0111_0111   0_0000_0011_0111
stopsys             0000_0000_0011_0110   000_0000_0111_0110   00_0000_0111_0110   0_0000_0011_0110
stt16     word      0000_001w_wwww_www0   000_0110_wwww_www0   00_0011_0www_www0   0_0000_110w_www0
sub       a,I       0001_1001_kkkk_kkkk   101_0001_kkkk_kkkk   10_1001_kkkk_kkkk   1_0001_kkkk_kkkk
sub       a,M       0100_011m_mmmm_mmmm   001_1001_mmmm_mmmm   00_1100_1mmm_mmmm   0_0110_01mm_mmmm
sub       M,a       0100_010m_mmmm_mmmm   001_0001_mmmm_mmmm   00_1000_1mmm_mmmm   0_0100_01mm_mmmm
subc      a         0000_0000_0001_0001   000_0000_0110_0001   00_0000_0110_0001   0_0000_0001_0001
subc      a,M       0100_111m_mmmm_mmmm   001_1011_mmmm_mmmm   00_1101_1mmm_mmmm   0_0110_11mm_mmmm
subc      M         0110_001m_mmmm_mmmm   010_0001_mmmm_mmmm   01_0000_1mmm_mmmm   0_1000_01mm_mmmm
subc      M,a       0100_110m_mmmm_mmmm   001_0011_mmmm_mmmm   00_1001_1mmm_mmmm   0_0100_11mm_mmmm
swap      a         0000_0000_0001_1110   000_0000_0110_1110   00_0000_0110_1110   0_0000_0001_1110
swap      M         0111_110m_mmmm_mmmm
swapc     IO.n      0010_111b_bbpp_pppp   101_11bb_bppp_pppp   00_010b_bbpp_pppp
t0sn      IO.n      0010_000b_bbpp_pppp   011_00bb_bppp_pppp   01_100b_bbpp_pppp   0_1100_bbbp_pppp
t0sn      M.n       1000_bbbm_mmmm_mmmm   100_00bb_bmmm_mmmm   10_000b_bbmm_mmmm   0_0010_bbb0_mmmm
t1sn      IO.n      0010_001b_bbpp_pppp   011_01bb_bppp_pppp   01_101b_bbpp_pppp   0_1101_bbbp_pppp
t1sn      M.n       1001_bbbm_mmmm_mmmm   100_01bb_bmmm_mmmm   10_001b_bbmm_mmmm   0_0010_bbb1_mmmm
tog       IO.n      0010_100b_bbpp_pppp
wait0     IO.n      0010_101b_bbpp_pppp
wait1     IO.n      0010_110b_bbpp_pppp
wdreset             0000_0000_0011_0000   000_0000_0111_0000   00_0000_0111_0000   0_0000_0011_0000
xch       M         0110_111m_mmmm_mmmm   010_0111_mmmm_mmmm   01_0011_1mmm_mmmm   0_1001_11mm_mmmm
xor       a,I       0001_1110_kkkk_kkkk   101_0110_kkkk_kkkk   10_1110_kkkk_kkkk   1_0110_kkkk_kkkk
xor       a,IO      0001_0000_01pp_pppp
xor       a,M       0101_101m_mmmm_mmmm   001_1110_mmmm_mmmm   00_1111_0mmm_mmmm   0_0111_10mm_mmmm
xor       IO,a      0001_0000_00pp_pppp   000_0000_1ppp_pppp   00_0000_11pp_pppp   0_0000_011p_pppp
xor       M,a       0101_100m_mmmm_mmmm   001_0110_mmmm_mmmm   00_1011_0mmm_mmmm   0_0101_10mm_mmmm

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 03, 2018, 08:30:32 pm

On the second day, wrt. completeness of implementation of the C standard, this has now far surpassed Mini-C.


Well done! Seems to be doing its job.

Code: [Select]
unsigned int a = 15;
unsigned int b = 23;
unsigned int c;

void
main( void ) {
while (c < a * b) {
c += a;
}
}

Weird: The compiler doesnt seem to realize that a*b will always be constant (even if I declare both variables as const and they land in the const segment).
Is that an optimization step?

Code: [Select]
...
_main:
; test.c: 7: while (c < a * b) {
00101$:
mov a, _a+0
mov __mulint_PARM_1+0, a
mov a, _a+1
mov __mulint_PARM_1+1, a
mov a, _b+0
mov __mulint_PARM_2+0, a
mov a, _b+1
mov __mulint_PARM_2+1, a
call __mulint
mov _main_sloc0_1_0+0, a
mov a, p
mov _main_sloc0_1_0+1, a
mov a, _c+0
sub a, _main_sloc0_1_0+0
mov a, _c+1
subc a, _main_sloc0_1_0+1
mov a, #0x00
slc a
mov _main_sloc1_1_0+0, a
mov a, _main_sloc1_1_0+0
cneqsn a, #0x00
goto 00104$
; test.c: 8: c += a;
mov a, _c+0
add a, _a+0
mov _c+0, a
mov a, _c+1
addc a, _a+1
mov _c+1, a
goto 00101$
00104$:
; test.c: 10: }
ret
...
__xinit__a:
.dw #0x000f
__xinit__b:
.dw #0x0017

Although init code seems to be missing and I get lot of this:

Code: [Select]
test.asm:60: Error: <a> machine specific addressing or addressing mode error
test.asm:61: Error: <a> machine specific addressing or addressing mode error
test.asm:62: Error: <a> machine specific addressing or addressing mode error
test.asm:63: Error: <a> machine specific addressing or addressing mode error
test.asm:64: Error: <a> machine specific addressing or addressing mode error
test.asm:65: Error: <a> machine specific addressing or addressing mode error
test.asm:66: Error: <a> machine specific addressing or addressing mode error
test.asm:67: Error: <a> machine specific addressing or addressing mode error
test.asm:69: Error: <a> machine specific addressing or addressing mode error
test.asm:70: Error: <a> machine specific addressing or addressing mode error
test.asm:71: Error: <a> machine specific addressing or addressing mode error
test.asm:72: Error: <a> machine specific addressing or addressing mode error
test.asm:74: Error: <a> machine specific addressing or addressing mode error
test.asm:75: Error: <o> .org in REL area or directive / mnemonic error
test.asm:76: Error: <a> machine specific addressing or addressing mode error
test.asm:77: Error: <o> .org in REL area or directive / mnemonic error
test.asm:78: Error: <a> machine specific addressing or addressing mode error
test.asm:79: Error: <a> machine specific addressing or addressing mode error
test.asm:80: Error: <o> .org in REL area or directive / mnemonic error
test.asm:81: Error: <q> missing or improper operators, terminators, or delimiters
test.asm:83: Error: <a> machine specific addressing or addressing mode error
test.asm:85: Error: <a> machine specific addressing or addressing mode error
test.asm:86: Error: <a> machine specific addressing or addressing mode error
test.asm:87: Error: <o> .org in REL area or directive / mnemonic error
test.asm:88: Error: <a> machine specific addressing or addressing mode error
test.asm:89: Error: <q> missing or improper operators, terminators, or delimiters
removing test.rel
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 04, 2018, 04:14:49 am
PFS173 startup code

Edit: fixed disassembler bug that caused IO addresses > 63 to be incorrect, and all bit addresses to be incorrect

Code: [Select]
PDK version: 20
PDK data size:  3072 words
Free data size: 3040 words
MCU: PFS173 [ID: 0x2AA2]
Compiler version: 0.84
15 bit core
0000  5700  mov       a, 0x00
0001  0102  mov       SP, a
0002  7BED  call      0x0BED
0003  010B  mov       IHRCR, a
0004  7BEE  call      0x0BEE
0005  0163  mov       BGTR, a
0006  5770  mov       a, 0x70
0007  0128  mov       MISC_LVR, a
0008  573C  mov       a, 0x3C
0009  0103  mov       CLKCMD, a
000A  57F9  mov       a, 0xF9
000B  010D  mov       PADIER, a
000C  57FF  mov       a, 0xFF
000D  010E  mov       PBDIER, a
000E  570F  mov       a, 0x0F
000F  010F  mov       PCDIER, a
0010  5700  mov       a, 0x00
0011  0167  mov       ROP, a
0012  7BFE  call      0x0BFE
0013  52FF  ceqsn     a, 0xFF
0014  6059  goto      0x0059
0015  7BED  call      0x0BED
0016  1701  mov       M1, a
0017  3F11  set1      PAC.6
0018  5709  mov       a, 0x09
0019  1700  mov       M0, a
001A  3590  t1sn      PA.3
001B  601A  goto      0x001A
001C  3F10  set1      PA.6
001D  0063  dzsn      a
001E  601D  goto      0x001D
001F  2300  dzsn      M0
0020  601D  goto      0x001D
0021  3B10  set0      PA.6
0022  3190  t0sn      PA.3
0023  6022  goto      0x0022
0024  5701  mov       a, 0x01
0025  3290  t0sn      PA.5
0026  57FF  mov       a, 0xFF
0027  1801  add       a, M1
0028  010B  mov       IHRCR, a
0029  1701  mov       M1, a
002A  3590  t1sn      PA.3
002B  602A  goto      0x002A
002C  3690  t1sn      PA.5
002D  6054  goto      0x0054
002E  5704  mov       a, 0x04
002F  0126  mov       MISC, a
0030  3190  t0sn      PA.3
0031  6030  goto      0x0030
0032  2604  clear     M4
0033  2605  clear     M5
0034  575A  mov       a, 0x5A
0035  1702  mov       M2, a
0036  5700  mov       a, 0x00
0037  1703  mov       M3, a
0038  0502  ldtabl    M2
0039  1604  xor       M4, a
003A  0503  ldtabh    M2
003B  1005  add       M5, a
003C  2B04  sl        M4
003D  2D05  slc       M5
003E  2004  addc      M4
003F  2502  dec       M2
0040  2103  subc      M3
0041  3480  t1sn      FLAG.C
0042  6038  goto      0x0038
0043  3F10  set1      PA.6
0044  3590  t1sn      PA.3
0045  6044  goto      0x0044
0046  2B04  sl        M4
0047  2D05  slc       M5
0048  5F10  swapc     PA.6
0049  3190  t0sn      PA.3
004A  6049  goto      0x0049
004B  3290  t0sn      PA.5
004C  6044  goto      0x0044
004D  3B10  set0      PA.6
004E  3590  t1sn      PA.3
004F  604E  goto      0x004E
0050  3190  t0sn      PA.3
0051  6050  goto      0x0050
0052  3690  t1sn      PA.5
0053  6032  goto      0x0032
0054  3190  t0sn      PA.3
0055  6054  goto      0x0054
0056  3690  t1sn      PA.5
0057  6018  goto      0x0018
0058  6058  goto      0x0058
0059  010B  mov       IHRCR, a
005A  605A  goto      0x005A
005B  7FFF  call      0x0FFF
005C  7FFF  call      0x0FFF
005D  7FFF  call      0x0FFF
005E  7FFF  call      0x0FFF
005F  7FFF  call      0x0FFF
0060  7FFF  call      0x0FFF
...
0BE0  7FFF  call      0x0FFF
0BE1  7FFF  call      0x0FFF
0BE2  7FFF  call      0x0FFF
0BE3  7FFF  call      0x0FFF
0BE4  7FFF  call      0x0FFF
0BE5  7FFF  call      0x0FFF
0BE6  7FFF  call      0x0FFF
0BE7  7FFF  call      0x0FFF
0BE8  7FFF  call      0x0FFF
0BE9  7FFF  call      0x0FFF
0BEA  7FFF  call      0x0FFF
0BEB  7FFF  call      0x0FFF
0BEC  7FFF  call      0x0FFF
0BED  7FFF  call      0x0FFF
0BEE  7FFF  call      0x0FFF
0BEF  3FFE  set1      io.126.7
0BF0  7FFF  call      0x0FFF
0BF1  7FFF  call      0x0FFF
0BF2  7FFF  call      0x0FFF
0BF3  7FFF  call      0x0FFF
0BF4  7FFF  call      0x0FFF
0BF5  7FFF  call      0x0FFF
0BF6  7FFF  call      0x0FFF
0BF7  7FFF  call      0x0FFF
0BF8  0000  nop
0BF9  0000  nop
0BFA  7FFF  call      0x0FFF
0BFB  7FFF  call      0x0FFF
0BFC  7FFF  call      0x0FFF
0BFD  7FFF  call      0x0FFF
0BFE  7FFF  call      0x0FFF
0BFF  7AFC  call      0x0AFC
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 07:16:17 am
Now that the software side seems on track, how about some hardware engineering?

It should be possible to program the chips with xFFF so they stay fresh and useable.
Just for a quick peek at what the programmer does.
We should now be able to distinguish between the programming phase and the bit-banged calibration.
Maybe start with the PFS154 (dont have a programmer, I do have an arduino ;)? I have some of those and I suspect that reprogrammable chips are most interesting at this stage.

Or maybe analyse the bitstream from the Cypress chip to the FPGA on the ICE so we can understand what chip is being used?
Or even simpler: take the FPGA out and see whether the ICE even notices ;)

Anyone?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 04, 2018, 09:58:45 am
Although init code seems to be missing and I get lot of this:

Code: [Select]
test.asm:60: Error: <a> machine specific addressing or addressing mode error
[…]

You can compile to asm using -S to avoid those error messages (without -S, SDCC tries to invoke an Assembler, which currently happens to be one for STM8).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 12:51:04 pm
Ok, with that the error messages are now

Code: [Select]


Nice  :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 04, 2018, 12:54:14 pm
Now that the software side seems on track, how about some hardware engineering?

It should be possible to program the chips with xFFF so they stay fresh and useable.
Just for a quick peek at what the programmer does.
We should now be able to distinguish between the programming phase and the bit-banged calibration.

Currently I'm designing a 4 channel (optionally 8 channel) ADC with at least 10 MHz sample rate and 1 GB RAM:

https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/ (https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/)

Parts are ordered, I just need to layout it and order the PCB, then write the software for the DE10 Nano for it. Might need a few weeks, but then I can sample a full programming cycle with all pins in parallel. This should make it much easier to reverse engineer the exact protocol and to reproduce it. The software should be no problem, I've done this before (http://www.frank-buss.de/parallella/sampler/).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 01:38:17 pm
I ran the regression tests in sdcc/src/regression and most of them seem to run fine.
Sometimes there are "FATAL Compiler Internal Error" that are specfic to the pdk14 backend

find -iname \*\.c -exec sh -c "echo {} ; sdcc -S -mpdk14 {}" \;

Code: [Select]
./switch1.c
./rotate6.c
./rotate6.c:86: warning 94: comparison is always true due to limited range of data type
./rotate6.c:84: warning 158: overflow in implicit constant conversion
./rotate6.c:121: warning 158: overflow in implicit constant conversion
./compare3.c
./compare3.c:151: warning 94: comparison is always false due to limited range of data type
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:173: warning 94: comparison is always false due to limited range of data type
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./rotate1.c
./compare7.c
In file included from ./compare7.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./compare5.c
./compare5.c:219: warning 94: comparison is always false due to limited range of data type
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:242: warning 94: comparison is always false due to limited range of data type
./compare5.c:271: warning 94: comparison is always false due to limited range of data type
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare6.c
Backtrace:
sdcc(+0xa4bce)[0x55b8eaabbbce]
sdcc(+0x1d73a7)[0x55b8eabee3a7]
sdcc(+0x1d7946)[0x55b8eabee946]
sdcc(+0x1d9c1e)[0x55b8eabf0c1e]
sdcc(+0x1d671e)[0x55b8eabed71e]
sdcc(+0x3c35c)[0x55b8eaa5335c]
sdcc(+0x568b0)[0x55b8eaa6d8b0]
sdcc(+0x1fe9f)[0x55b8eaa36e9f]
sdcc(+0x1be86)[0x55b8eaa32e86]
/lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xe7)[0x7fde56ffdb97]
sdcc(+0x1d7aa)[0x55b8eaa347aa]
./compare6.c:165: error 9: FATAL Compiler Internal Error in file 'gen.c' line number '265' : code generator internal error
Contact Author with source code
Caught signal 11: SIGSEGV
./bool2.c
./nestfor.c
In file included from ./nestfor.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./pcodeopt.c
./struct1.c
./compare8.c
In file included from ./compare8.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./rotate3.c
./ptrarg.c
./add3.c
./add3.c:64: warning 94: comparison is always true due to limited range of data type
./rotate2.c
./call1.c
./bool1.c
./compare4.c
./compare4.c:63: warning 94: comparison is always false due to limited range of data type
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:93: warning 94: comparison is always false due to limited range of data type
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:250: warning 94: comparison is always true due to limited range of data type
./compare4.c:294: warning 158: overflow in implicit constant conversion
./compare4.c:304: warning 158: overflow in implicit constant conversion
./compare4.c:313: warning 158: overflow in implicit constant conversion
./rotate4.c
./rotate4.c:30: error 9: FATAL Compiler Internal Error in file 'gen.c' line number '1520' : Unimplemented iCode
Contact Author with source code
./add2.c
./compare10.c
In file included from ./compare10.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./inline.c
In file included from ./inline.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./rotate5.c
./rotate5.c:179: warning 158: overflow in implicit constant conversion
./rotate5.c:205: warning 158: overflow in implicit constant conversion
./rotate5.c:206: warning 158: overflow in implicit constant conversion
./rotate5.c:209: warning 158: overflow in implicit constant conversion
./rotate5.c:210: warning 158: overflow in implicit constant conversion
./rotate5.c:213: warning 158: overflow in implicit constant conversion
./rotate5.c:216: warning 158: overflow in implicit constant conversion
./rotate5.c:219: warning 158: overflow in implicit constant conversion
./rotate5.c:222: warning 158: overflow in implicit constant conversion
./rotate5.c:225: warning 158: overflow in implicit constant conversion
./rotate5.c:228: warning 158: overflow in implicit constant conversion
./rotate5.c:229: warning 158: overflow in implicit constant conversion
./bool3.c
./string1.c
In file included from ./string1.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./xor.c
./compare.c
./compare9.c
In file included from ./compare9.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./for.c
./for.c:37: error 226: no type specifier for '(cast)'
./add4.c
./add.c
./pointer1.c
./and1.c
./and2.c
./b.c
./ptrfunc.c
./ptrfunc.c:47: error 9: FATAL Compiler Internal Error in file 'gen.c' line number '516' : Unimplemented call through function pointer
Contact Author with source code
./compare2.c
./mult1.c
./sub.c
./rotate7.c
./rotate7.c:206: warning 158: overflow in implicit constant conversion
./rotate7.c:212: warning 158: overflow in implicit constant conversion
./rotate7.c:218: warning 158: overflow in implicit constant conversion
./rotate7.c:224: warning 158: overflow in implicit constant conversion
./rotate7.c:230: warning 158: overflow in implicit constant conversion
./rotate7.c:236: warning 158: overflow in implicit constant conversion
./rotate7.c:242: warning 158: overflow in implicit constant conversion
./rotate7.c:248: warning 158: overflow in implicit constant conversion
./rotate7.c:254: warning 158: overflow in implicit constant conversion
./rotate7.c:260: warning 158: overflow in implicit constant conversion
./rotate7.c:266: warning 158: overflow in implicit constant conversion
./rotate7.c:272: warning 158: overflow in implicit constant conversion
./rotate7.c:278: warning 158: overflow in implicit constant conversion
./rotate7.c:284: warning 158: overflow in implicit constant conversion
./rotate7.c:290: warning 158: overflow in implicit constant conversion
./rotate7.c:297: warning 158: overflow in implicit constant conversion
./rotate7.c:303: warning 158: overflow in implicit constant conversion
./rotate7.c:309: warning 158: overflow in implicit constant conversion
./rotate7.c:315: warning 158: overflow in implicit constant conversion
./rotate7.c:321: warning 158: overflow in implicit constant conversion
./rotate7.c:327: warning 158: overflow in implicit constant conversion
./rotate7.c:333: warning 158: overflow in implicit constant conversion
./rotate7.c:339: warning 158: overflow in implicit constant conversion
./rotate7.c:345: warning 158: overflow in implicit constant conversion
./rotate7.c:351: warning 158: overflow in implicit constant conversion
./rotate7.c:357: warning 158: overflow in implicit constant conversion
./rotate7.c:363: warning 158: overflow in implicit constant conversion
./rotate7.c:369: warning 158: overflow in implicit constant conversion
./rotate7.c:375: warning 158: overflow in implicit constant conversion
./rotate7.c:381: warning 158: overflow in implicit constant conversion
./init0.c
./init0.c:43: error 9: FATAL Compiler Internal Error in file 'gen.c' line number '516' : Unimplemented call through function pointer
Contact Author with source code
./while.c
./empty.c
./arrays.c
./or1.c
./sub2.c
./sub2.c:162: warning 158: overflow in implicit constant conversion
./configword.c
In file included from ./configword.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./bank1.c
./bank1.c:20: error 9: FATAL Compiler Internal Error in file 'SDCCmem.c' line number '385' : code generator internal error
Contact Author with source code
Caught signal 11: SIGSEGV


find -iname \*\.c -exec sh -c "echo {} ; sdcc -S -mmcs51 {}" \;

Code: [Select]
./switch1.c
./rotate6.c
./rotate6.c:86: warning 94: comparison is always true due to limited range of data type
./rotate6.c:84: warning 158: overflow in implicit constant conversion
./rotate6.c:121: warning 158: overflow in implicit constant conversion
./compare3.c
./compare3.c:151: warning 94: comparison is always false due to limited range of data type
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:152: warning 126: unreachable code
./compare3.c:173: warning 94: comparison is always false due to limited range of data type
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./compare3.c:174: warning 126: unreachable code
./rotate1.c
./compare7.c
In file included from ./compare7.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./compare5.c
./compare5.c:219: warning 94: comparison is always false due to limited range of data type
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:220: warning 126: unreachable code
./compare5.c:242: warning 94: comparison is always false due to limited range of data type
./compare5.c:271: warning 94: comparison is always false due to limited range of data type
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:243: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare5.c:272: warning 126: unreachable code
./compare6.c
./bool2.c
./nestfor.c
In file included from ./nestfor.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./pcodeopt.c
./struct1.c
./compare8.c
In file included from ./compare8.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./rotate3.c
./ptrarg.c
./add3.c
./add3.c:64: warning 94: comparison is always true due to limited range of data type
./rotate2.c
./call1.c
./bool1.c
./compare4.c
./compare4.c:63: warning 94: comparison is always false due to limited range of data type
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:64: warning 126: unreachable code
./compare4.c:93: warning 94: comparison is always false due to limited range of data type
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:94: warning 126: unreachable code
./compare4.c:250: warning 94: comparison is always true due to limited range of data type
./compare4.c:294: warning 158: overflow in implicit constant conversion
./compare4.c:304: warning 158: overflow in implicit constant conversion
./compare4.c:313: warning 158: overflow in implicit constant conversion
./rotate4.c
./add2.c
./compare10.c
In file included from ./compare10.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./inline.c
In file included from ./inline.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./rotate5.c
./rotate5.c:179: warning 158: overflow in implicit constant conversion
./rotate5.c:205: warning 158: overflow in implicit constant conversion
./rotate5.c:206: warning 158: overflow in implicit constant conversion
./rotate5.c:209: warning 158: overflow in implicit constant conversion
./rotate5.c:210: warning 158: overflow in implicit constant conversion
./rotate5.c:213: warning 158: overflow in implicit constant conversion
./rotate5.c:216: warning 158: overflow in implicit constant conversion
./rotate5.c:219: warning 158: overflow in implicit constant conversion
./rotate5.c:222: warning 158: overflow in implicit constant conversion
./rotate5.c:225: warning 158: overflow in implicit constant conversion
./rotate5.c:228: warning 158: overflow in implicit constant conversion
./rotate5.c:229: warning 158: overflow in implicit constant conversion
./bool3.c
./string1.c
In file included from ./string1.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./xor.c
./compare.c
./compare9.c
In file included from ./compare9.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./for.c
./for.c:37: error 226: no type specifier for '(cast)'
./add4.c
./add.c
./pointer1.c
./and1.c
./and2.c
./b.c
./ptrfunc.c
./compare2.c
./mult1.c
./sub.c
./rotate7.c
./rotate7.c:206: warning 158: overflow in implicit constant conversion
./rotate7.c:212: warning 158: overflow in implicit constant conversion
./rotate7.c:218: warning 158: overflow in implicit constant conversion
./rotate7.c:224: warning 158: overflow in implicit constant conversion
./rotate7.c:230: warning 158: overflow in implicit constant conversion
./rotate7.c:236: warning 158: overflow in implicit constant conversion
./rotate7.c:242: warning 158: overflow in implicit constant conversion
./rotate7.c:248: warning 158: overflow in implicit constant conversion
./rotate7.c:254: warning 158: overflow in implicit constant conversion
./rotate7.c:260: warning 158: overflow in implicit constant conversion
./rotate7.c:266: warning 158: overflow in implicit constant conversion
./rotate7.c:272: warning 158: overflow in implicit constant conversion
./rotate7.c:278: warning 158: overflow in implicit constant conversion
./rotate7.c:284: warning 158: overflow in implicit constant conversion
./rotate7.c:290: warning 158: overflow in implicit constant conversion
./rotate7.c:297: warning 158: overflow in implicit constant conversion
./rotate7.c:303: warning 158: overflow in implicit constant conversion
./rotate7.c:309: warning 158: overflow in implicit constant conversion
./rotate7.c:315: warning 158: overflow in implicit constant conversion
./rotate7.c:321: warning 158: overflow in implicit constant conversion
./rotate7.c:327: warning 158: overflow in implicit constant conversion
./rotate7.c:333: warning 158: overflow in implicit constant conversion
./rotate7.c:339: warning 158: overflow in implicit constant conversion
./rotate7.c:345: warning 158: overflow in implicit constant conversion
./rotate7.c:351: warning 158: overflow in implicit constant conversion
./rotate7.c:357: warning 158: overflow in implicit constant conversion
./rotate7.c:363: warning 158: overflow in implicit constant conversion
./rotate7.c:369: warning 158: overflow in implicit constant conversion
./rotate7.c:375: warning 158: overflow in implicit constant conversion
./rotate7.c:381: warning 158: overflow in implicit constant conversion
./init0.c
./while.c
./empty.c
./arrays.c
./or1.c
./sub2.c
./sub2.c:162: warning 158: overflow in implicit constant conversion
./configword.c
In file included from ./configword.c:2:
./picregs.h:6:25: fatal error: pic14regs.h: No such file or directory
compilation terminated.
./picregs.h:1: warning 190: ISO C forbids an empty source file
./bank1.c
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 03:08:49 pm
Might need a few weeks, but then I can sample a full programming cycle with all pins in parallel.

Yeah, I was rather hoping someone would be in for something quick & dirty   :-DD
(Just so you get me right I think its great and well worth it in the long run, but to keep things moving something more light weight might be what we need right now)

My theory (as pointed out by others as well and assuming the chip is reasonably akin to something like the old pics is that:

The first voltage spike + shoulder selects a programming mode of some sort.
Then you would send a short command/address and maybe some data.

Code: [Select]
         |\
         |  \
         |   \______   _______
         |          | |       |
         |          |_|       | .........

         |- select -||-----command / data-----   
             mode

My hope is that no very long duration is needed for signal analysis but just the very few first cycles.
That would be enough to start getting an arduino to do the same and see what happens  :popcorn:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 04:26:09 pm
A good starting point to see what I mean might be this datasheet for old PIC16C7XX OTPs
(although the padauks will probably behave differently I guess its reasonable to assume for now that their approach is similar)

http://ww1.microchip.com/downloads/en/DeviceDoc/30298d.pdf (http://ww1.microchip.com/downloads/en/DeviceDoc/30298d.pdf)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 04, 2018, 08:03:34 pm
The remark "Please notice that bit 0 should be kept 0 due to program counter is 16 bits" in the datasheets seems odd to me. Any idea, what this could be about? Would anything break if I place the stack at an odd address? Do push / pop / call / ret require the stack pointer to be aligned?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 04, 2018, 08:42:37 pm
The remark "Please notice that bit 0 should be kept 0 due to program counter is 16 bits" in the datasheets seems odd to me. Any idea, what this could be about? Would anything break if I place the stack at an odd address? Do push / pop / call / ret require the stack pointer to be aligned?

Philipp


Well it says "should be" not "must be". Hard to tell without an actual device or the ICE.

Depends on how they implemented the actual logic.
If it just takes the MSBs and toggles the last bit, then placing it an odd address will give you the byte in front of it.
Could make sense if you dont want to add the one. Probably makes sense because it saves space on the die (you'd have to do some arithmetic to get the result right otherwise)

consider this: you place sp at 0x3f then sp+1 is 0x40
You need to add an 7 bit adder for that (if I counted that right) thats significantly more computationally intensive (ie more die space) than toggle bit 0. Can all be done, by utilising the ALU for example but then speed is an issue, so I guess they dont.

looking at the datasheets again they might actually do a single cycle 16-bit access ie. ignore the lowest bit entirely
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 04, 2018, 11:44:36 pm
I interpret this to mean that the RAM is word accessible only on word boundaries. Bit 0 of SP must be 0 to ensure word alignment. This implies that push/pop af will use a word of stack instead of a byte.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 05, 2018, 05:54:09 am
I think if you could revers the programmer too, it would be like heaven! ;) ;)

Guys Thanks for the great work and collaboration. :) :-+ :-+ :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 07:01:41 am
I interpret this to mean that the RAM is word accessible only on word boundaries. Bit 0 of SP must be 0 to ensure word alignment. This implies that push/pop af will use a word of stack instead of a byte.

pushaf/popaf always use a word hence the +2

Result:        [sp] ← {flag, ACC};
sp ← sp + 2 ;

I guess they optimized this for call/ret which need 16/15/14/13 bit and not just a byte.
And other instructions then just use the same mechanism that is already in place.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 05, 2018, 08:20:13 am
Another question on push af  would be which one of a and f goes into the lower address.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 09:04:03 am
Another question on push af  would be which one of a and f goes into the lower address.

Philipp


Doesnt really matter does it?

If you implement pushaf and popaf symetrically for an emulator there will be no difference.
A isn't used as return value (thats the whole point of pushing it).
Unless youre trying to expicitly modify A or the flags on the stack there is absolutely no difference. They are designed to be atomic operations.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 05, 2018, 09:12:54 am
Another question on push af  would be which one of a and f goes into the lower address.

Philipp


Doesnt really matter does it?

If you implement pushaf and popaf symetrically for an emulator there will be no difference.
A isn't used as return value (thats the whole point of pushing it).
Unless youre trying to expicitly modify A or the flags on the stack there is absolutely no difference. They are designed to be atomic operations.

It matters: Pushing data on the stack has its uses. E.g. for a call via a function pointer:

Code: [Select]
pushw #retlabel
pushw funcptr
ret
retlabel:

To emulate one pushw (which is not available on most devices) 8 instructions are generated by SDCC (p is a pseudoregister in RAM):

Code: [Select]
ld a, sp
ld p, a
push af
ld a, op0
idxm p, a
inc p
ld a, op1
idxm p, a

That could obviously be brought down to 6 or 7 (depending on which byte a goes in on push af).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 05, 2018, 10:06:57 am
Updated disassembler with 15 bit instruction set support.

Linux and Windows binaries included.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 10:16:51 am

That could obviously be brought down to 6 or 7 (depending on which byte a goes in on push af).

Philipp

I dont quite understand why there is pushaf at all (I assume ld = mov)


Code: [Select]
mov a, sp;                  a = sp
mov p, a;                 p = a
push af    // a is already overwritten by sp so why save it? shouldn't this be the first instruction?
mov a, op0;               a = op0
idxm p, a;                  [p] = a
inc p;                          p += 1
mov a, op1;               a = op1
idxm p, a;                  [p] = a

I would imagine that something like this would be appropriate:

Code: [Select]
pushaf
mov a, sp
mov p, a
mov a, op0
idxm p, a
inc a
mov a, op1
idxm p, a
add sp, 2

Still dont see why the order in which a and flags are pushed would change this
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 10:19:55 am
You could also write something shorter like this. Still if you implement this symmetrically for pop there is no problem whatsoever even if the real hardware would behave differently.

edit: check the sp calculations on this chip sp grows up not down. Also what happens when an interrupt occurs and sp is increased by one?

Code: [Select]
pushaf
mov a, op0
idxm sp, a
inc sp
mov a, op1
idxm sp, a
inc sp



Code: [Select]
dec sp
idxm a, sp
mov op1, a
dec sp
idxm a, sp
mov op0, a
popaf
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 05, 2018, 10:21:16 am
Yes, I meant mov, not ld.

The push af is curently just used to cheaply increase sp by 2. But If I knew which byte a goes into, it could be used to at the same time write one of the bytes I want on the stack.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 10:32:49 am
Yes, I meant mov, not ld.

The push af is curently just used to cheaply increase sp by 2. But If I knew which byte a goes into, it could be used to at the same time write one of the bytes I want on the stack.

Philipp


But then you dont need the pushaf/popaf at all and youre down to six instructions anyway ;)

Code: [Select]
mov a, op0
idxm sp, a
inc sp
mov a, op1
idxm sp, a
inc sp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 05, 2018, 10:36:07 am
But then you dont need the pushaf/popaf at all and youre down to six instructions anyway ;)

Code: [Select]
mov a, op0
idxm sp, a
inc sp
mov a, op1
idxm sp, a
inc sp

sp is in IO space, so there is no inc sp, and no idxm sp, a.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 10:44:44 am
ok now i get you would like to do something like this:

Code: [Select]
mov a, sp
mov p, a
mov a, op0
pushaf
inc p
mov a, op1
idxm p, a
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 10:51:19 am
you could of course also do

Code: [Select]
mov a, op0
pushaf
mov a, op1
pushaf
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 11:02:42 am
I looked at the PMC884 datasheet and you really cannot infer the positions on the stack.

        word          data0  ;                        //  declare  data0 in RAM
        word          data1  ;                        //  declare  data1 in RAM
        ...
mov       a, 0x55 ;
mov       ld@data0,  a  ;            //  move  0x55  to  data0 (LSB)
mov       a, 0xaa ;
mov       hd@data0, a  ;          //  move  0xaa  to  data0 (MSB)
pushw   data0  ;                      //  move  data (0xaa, 0x55) to stack memory (word)
popw     data1  ;                      //  move  (0xaa,  0x55)  in stack memory to data1 (word)
mov       a,  ld@data1  ;            //  ACC=0x55
mov       a,  hd@data1  ;            // ACC=0xaa
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 12:14:54 pm
Updated disassembler with 15 bit instruction set support.

Linux and Windows binaries included.


There seems to be a small problem with the io.txt file for the 15-bit core: some of the ios are no longer named (PFS173 startup code). PFS154 and test pdks previously included work fine.

Code: [Select]
001D  3F10  set1      .6
001E  0063  dzsn      a
001F  601E  goto      0x001E
0020  2300  dzsn      M0
0021  601E  goto      0x001E
0022  3B10  set0      .6
0023  3190  t0sn      .3
0024  6023  goto      0x0023
0025  5701  mov       a, 0x01
0026  3290  t0sn      .5
0027  57FF  mov       a, 0xFF
0028  1801  add       a, M1
0029  010B  mov       IHRCR, a
002A  1701  mov       M1, a
002B  3590  t1sn      .3
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 05, 2018, 12:19:41 pm
I looked at the PMC884 datasheet and you really cannot infer the positions on the stack.

        word          data0  ;                        //  declare  data0 in RAM
        word          data1  ;                        //  declare  data1 in RAM
        ...

From the startup code and the description of idxm one can infer that the Padauks are little endian, so the byte order for pusw in the 16-Bit instruction set should be the same. But push af is a different matter. Doing push af twice won't push a 16-Bit value onto the stack. It pushes two 16-bit vales, and the two a value bytes are apart, so I can't use that to push a 16-bit value.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 12:33:30 pm

From the startup code and the description of idxm one can infer that the Padauks are little endian, so the byte order for pusw in the 16-Bit instruction set should be the same. But push af is a different matter. Doing push af twice won't push a 16-Bit value onto the stack. It pushes two 16-bit vales, and the two a value bytes are apart, so I can't use that to push a 16-bit value.

No. idxm only moves a single byte from an index that is word aligned. So 16-bit address, 8-bit data (A isnt 16-bits), two idxm's for one 16-bit operand.
I thought op0 is the low byte and op1 the high byte of op.

So still two pushaf's will push the low and high byte but not consecutive in memory which doesnt matter that much because most people wont be doing deeply nested loops or recursion on these things. Also its guranteed to work no matter what the actual design is.

So this should work:

Code: [Select]
word op;
....
mov a, ld@op //low byte of op
pushaf
mov a, hd@op //high byte of op
pushaf
...
popaf
mov hd@op, a
popaf
mov ld@op, a
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 05:38:04 pm
quick question about the ice:

is there a device driver disk or something?
The downloadable IDE doesnt install a driver somewhere does it?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 05, 2018, 06:07:46 pm
Hi,

the ICE and the WRITER use USB-HID to communicate. USB-HID is not the fastest option... but it does not need any driver on Windows/Linux/Mac/...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 06:12:42 pm
Ok, then I need to figure out how to get the firmware onto the naked dev boards I got today.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 06:28:37 pm
Also raises the interesting question what the P5SP firmwares are.
The firmware for the Cypresschip (*HID I presume) has about the right size for the chip, but the P5SP* files are ten times as large and wouldnt fit.

Maybe the socketed chip is a microcontroller after all and not an FPGA  :popcorn:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 05, 2018, 07:01:40 pm
Ok so I have found the bytes that need to be programmed at the start of the eeprom on the ICE close to the Cypress Chip:

C2 97 07 02 70 01 80 04 // this should be the ICE VID: 0797 PID: 7002 Revision/DID: 8001

C2 B4 04 04 10 01 A0 04 // This is the bulkloop firmware example from Cypress

C2 97 07 01 70 01 00 04 // ? with the controller loading the program from the EEPROM

C0 97 07 01 70 01 00 04 // ? EEPROM only holds VID/PID

Also something firmware ish is contained in FPPA_IDE.exe between 0x22af9c and 0x22ce77 (<- uncertain about the end and whether there might actually be two different firmwares here, also weird mix of .bin and .iic formats)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 05, 2018, 11:46:55 pm
There seems to be a small problem with the io.txt file for the 15-bit core: some of the ios are no longer named (PFS173 startup code). PFS154 and test pdks previously included work fine.

CR/LF line termination was not handled properly on the Linux version. Fixed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: amyk on December 06, 2018, 01:12:09 am
A good starting point to see what I mean might be this datasheet for old PIC16C7XX OTPs
(although the padauks will probably behave differently I guess its reasonable to assume for now that their approach is similar)

http://ww1.microchip.com/downloads/en/DeviceDoc/30298d.pdf (http://ww1.microchip.com/downloads/en/DeviceDoc/30298d.pdf)
I think they're more complex than that --- the PIC only uses the high voltage to enter programming mode and then it's just data/clock. In the video you can see more voltage levels than that.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 06, 2018, 07:56:45 am
I think they're more complex than that --- the PIC only uses the high voltage to enter programming mode and then it's just data/clock. In the video you can see more voltage levels than that.

On the PICs its not just the high voltage:
"The  Program/Verify  mode  is  entered  by  holding  pins RB6 and RB7 low, while raising MCLR pin from VSS to the appropriate VIHH (high voltage). VDD is then raised from  VSS to  the  appropriate  VDD level.  Once  in  this mode, the user program memory and the configuration memory  can  be  accessed  and  programmed  in  serial fashion. "

The Padauks are different, but I dont think that we need the full waveform to be captured.
Just the maybe 30 - 40 cycles after each rise of VDD. The mode select is probably a combination of analog voltage levels and commands.
Also its much easier to trigger on a rising edge so the timinig issues that David was having shouldnt be that much of a problem.

There arent that many voltage levels either (I assume that VPP is supplied at pin PA5 and freely adjustable within the range below).

0x63421c 70 69 Please remove all IC, and check VDD,\nVPP(PA5), PA0 / 3 / 4 / 7 is 0 V
0x634264 30 29 Please check VPP (PA5) = 4.6V
0x634284 31 30 Please check VPP (PA5) = 11.3V
0x6342a4 24 23 Please check VDD = 5.5V
0x6342bc 24 23 Please check VDD = 7.5V
0x6342d4 24 23 Please check VDD = 3.3V

But unfortunately I dont have a programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 06, 2018, 08:25:24 am
The Padauks are different, but I dont think that we need the full waveform to be captured.
Just the maybe 30 - 40 cycles after each rise of VDD. The mode select is probably a combination of analog voltage levels and commands.
Also its much easier to trigger on a rising edge so the timinig issues that David was having shouldnt be that much of a problem.

There are different voltages on more pins than just VDD. But my board is routed now, will get the parts today, then I can print out the board to test for footprint errors and will get the final PCB in less than 2 weeks. Might be very useful for other things as well. I can connect two of these boards to a DE10 Nano. Then I have 8 analog (-10 V to +10 V) 8 bit channels with 50 MHz sample rate each, 1 GB sample memory, a FPGA and Linux on the board to pre-process the data if necessary, and gigabit ethernet to stream it in real time to a PC (at least 10 MHz samplerate with 8 channels should be possible in this mode).

(https://i.imgur.com/iXd0cpC.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 06, 2018, 08:45:49 am
There are different voltages on more pins than just VDD.

Do they have the same level as VDD?

Some pins just have short pulses for blank checking.

If I interpret the strings FPPA_IDE.exe correctly only VDD, VPP(PA5) and PA0 / 3 / 4 / 7 (plus GND obviously) are used.
The smallest chip I could find (PMS150C-U06) only has VDD, PA5, GND and 4/3 as well as 6.
So 3 (clock) and 4 (data) and thats it. (which also support Davids findings in the video for the PMC150C SO8)
And if remember correctly PA6 is used for that bit banging calibration thing.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 06, 2018, 09:34:27 am
Right, the voltage levels might be identical on VDD and the data pins. At least it was about 6.5 V for some data lines when I tested it:

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1986377/#msg1986377 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1986377/#msg1986377)

Maybe looking at the programmer circuit board might help with this, too, and the programmer firmware.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 06, 2018, 09:45:06 am
I still think the areas with 6.5V VDD are for verification purposes, there should also be parts close to 2V,
however from the current PMS150C datasheet:
Supply  Voltage 2.0V ~ 5.5V (Maximum Rating: 5.5V) *If VDD over maximum rating, it may lead to a permanent damage of IC.

I quote again from the PIC datasheet:
Programming Algorithm Requires Variable VDD
The  PIC16C7XX  uses  an  intelligent  algorithm.  The algorithm  calls  for  program  verification  at  VDDMIN  as well  as  VDDMAX.  Verification  at  VDDMIN
  ensures  good “erase  margin”.  Verification  at  VDDMAX ensures  good “program margin.”  The actual programming must be done with VDD in the VDDP
 range (4.75 - 5.25V). VDDP=VDD range required during programming. VDDMIN = minimum operating VDD spec for the part. VDDMAX = maximum operating VDD
 spec for the part. Programmers must verify the PIC16C7XX at its specified VDDMAX and VDDMIN levels. Since  Microchip may introduce  future  versions  of  the  PIC16C7XX  with  a broader V
DD range, it is best that these levels are user selectable (defaults are ok).
Note:
Any    programmer    not    meeting    these requirements  may  only  be  classified  as “prototype” or “development” programmer, but not a “production” quality programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 06, 2018, 10:32:56 pm
Hi,

I wrote a little program to find out how LDSPTL/LDSPTH are truly working.

The program uses LDSPTL/LDSPTH to dump the IC content and send it out via a soft spi. Then I used a STM32 and created a small capture program for the SPI which sends it to my computer via USB-Serial-Port.

First I checked flags by loading 0x00 to flags register, then execute the opcode, then output the content of flag register over spi, afterwards I loaded 0xFF to flags register and tried again.
Result: LDSPTL/LDSPTH do not alter any flags

Then I made a loop to dump the content of a PMS154B by setting SP to mem:0 and then incrementing the 16 bit value in mem:0 and mem:1.
Result: I got a complete dump of the code memory.
Upper bits of LDSPTH are reading 0 -> dump reads exactly same as content of PDK file (0x3FFF reads as 0x3FFF)
When the address in SP (can hold 16 bits) exceeds the code memory, the address just wraps around and starts reading from 0 again (NO CRASH)


Bonus: It also became visible what WRITER did to the last 32 reserved bytes in memory  :)

PDK-DATA last 32 bytes:

0000fe0: ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f
0000ff0: 00 00 00 00 ff 3f ff 3f ff 3f ff 3f ff 3f 51 11


Dump from PMC154B last 32 bytes:

0000fe0: ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f 5a 02 ff 3f
0000ff0: 2d 34 a5 3e ff 3f ff 3f ff 3f ff 3f 48 02 51 11


GREAT FUN! (just spent 3 cent :-DD)

JS

UPDATE:
More notes about "last 8 Words", security bit, ... here:
https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt

UPDATE:
Special code found and guessing what it can be here:
https://github.com/free-pdk/fppa-pdk-documentation/blob/master/SpecialCodeFoundInPMS154B.txt
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 17, 2018, 11:27:07 pm
Hi,

I finally got the time to use a logic analyzer (ZeroPlus Logic Cube LAP-C322000) to capture the writing of a program on a PFS154.

I had to "modify" the logic analyzer first: was a LAP-C16032 ($100, 32kBit, can soft mod to 128 kBit) => swap SRAM => is now a LAP-C162000 / LAP-C322000 (4MBit) ( https://hackaday.com/2010/03/30/zeroplus-logic-cube-modification/ )  ::)

The logic analyzer allows -30V / +30V on logic pins, so capturing the expected 0V - 12V from WRITER was no problem.
Later, after deciphering the logic of the flashing protocol it will be easy to measure and reapply the real voltages for programing.
On oscilloscope it looks like PA5 receives the programing voltage of up to 12V during writing and VDD receives a slightly higher voltage >= 6.5V (maybe for reading the IC).


So first I created a PDK from my "SimpleBlink" demo and used WRITER to "CONVERT" it to a different "PACKAGE" which lets you disable the PIN CHECK (WRITER will check for all pins to have no short) which is not required for programing.
(The PDK without the pin check is attached to this post)

Then I used WRITER to write it to a PFS154 using a "PADAUK P-003". The logic analyzer was connected to JP3 on bottom side of programmer (A0 = pin 1 of JP3) and logic analyzer GND was connected to a ground pin on programmer PCB.

You can see some screen shots of the capture below (focus on first data block, zoomed in, zoomed in more).
I grouped CLK and DATA into a BUS (SPI) so the software tried to decode some bits... unfortunately it seems a non standard 8 bit transmissions is used.

It looks like PADAUK ICs enter programing mode if PA5_ICVPP is present before VDD is applied. 


Since the ZeroPlus software requires a logic analyzer to be present I exported the captured data to a simple text file of 117 MB, compressed to 1MB 7-Zip (requires recent version of 7-Zip since LZMA2 is used to make it so small, hidden in a normal ZIP since forum does not allow .7z files).
The file contains all details about the capture (2MHz seems to be enough, I tried with 100MHz but did not see any pulses < 100 units)

As always,

Have fun!

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 18, 2018, 07:07:44 pm
You can see some screen shots of the capture below (focus on first data block, zoomed in, zoomed in more).
I grouped CLK and DATA into a BUS (SPI) so the software tried to decode some bits... unfortunately it seems a non standard 8 bit transmissions is used.

I guess the problem is that the clock is rather random (ie software generated, decision path dependent)
If I count the bits by hand I get
10100101   A5
10100101   A5
10100101   A5
10100110   A6
00011010   1A
10100001   A1

for the last picture.
Maybe thats A5: enter programming mode (could also be increase address), A6: write value (followed by value, is 1A the value for the configuration bits?), A1: program value followed by pause (self timing programming?)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 19, 2018, 04:43:03 pm
Hi,

I analyzed a bit more of the capture and could observe the following:

- first PA.5 is set to high (not sure which voltage is applied since logic analyzer does not provide this info, will find out later)

- 100µs later VDD is set to high (not sure which voltage is applied since logic analyzer does not provide this info, will find out later)

- 500µs later PA.3 (CLK) and PA.6 (DAT) are used to send 48 bit of data:  1010010110100101101001011001cccccccc10101010001 (A5A5A5A*CMD-BYTE*AA1) Note: AA1 might be from OTP-ID 2AA1 ?

- depending on command
 * no response expected:
   - 100µs later VDD is set to low
   - 250µs later PA.5 is set to low

 * response expected:
   - maybe DAT/CLK changes direction (driven by IC now)? --> any idea how to find out who is sending IC or WRITER?
   - response length depending of command
   - 100µs later VDD is set to low
   - 250µs later PA.5 is set to low

****

Following in this order been sent:

0x61 / no response (maybe writer stops after getting no response or does not even wait for response)
0x61 / response: 00111110111101111111111110000111111100000000000000011100011111110001000000000001111 (3F7BFFC3F8000E3F8800F)

0x31 / response: 0000 (very slow clocking)

0x66 / no response (execution time is very long before VDD/PA.5 going low)

0x70 / additional send data: 000000000010001111111111111111111111111111111111111111110011111110000 0 0 0 0 0 0 0 0 (last bits slow clocking) (4x 14bit data: 0x0008, 0x3FFF, 0x3FFF, 0x3FFF , 0x3F8 0 0..)

0x61 / no response (maybe writer stops after getting no response or does not even wait for response)

0x71 / additional send data: ( multiple times:  (4 x 14 bit data, ADR, slow clocks to process) )

0x61 / no response (maybe writer stops after getting no response or does not even wait for response)
0x61 / no response (maybe writer stops after getting no response or does not even wait for response)
0x61 / response: ...
0x61 / no response (execution time is very very very long VDD/PA.5 going low, seems DAT pulses without CLK from IC extend waiting period)

0x70 / additional send data: ( multiple times:  (4 x 14 bit data, ADR?, slow clocks to process) )
0x70 / additional send data: ( multiple times:  (4 x 14 bit data, ADR?, slow clocks to process) )

0x61 / response: ...

0x60 / response: multiple times: (14 bit data)

0x61 / no response (maybe writer stops after getting no response or does not even wait for response)

0x60 / no response (maybe writer stops after getting no response or does not even wait for response)

0x70 / additional send data: ( multiple times:  (4 x 14 bit data, ADR, slow clocks to process) )

****

- now IC is booted normally (PA.5 stays low, VDD is set to high)

- at this point it looks like the "calibration code" is executed
  # PA.5 is set high
  # PA.4 + PA.7 output high some clocks later
  lot of PA.4/PA.3 communication is done ...

- after some time VDD is set to low (IC shutdown)

****

- calibration is run again

****

0x71 / additional send data: ( multiple times:  (4 x 14 bit data, ARD?, slow clocks to process) )

0x61 / response: ...

0x60 / no response (maybe writer stops after getting no response or does not even wait for response)

0x71 / additional send data: ( multiple times:  (4 x 14 bit data, ADR?, slow clocks to process) )

****

ALL DONE



Looks like:
 0x60/0x61 might be GET_STATUS or READ
 0x70/0x71 might be WRITE
 0x31 might be ERASE
 0x66 might be CHECKBLANK


Time to write a parser for this  :)

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on December 19, 2018, 04:52:27 pm
You can hook if a few analog comparators to diffetentiate between the required voltage levels. Something like a flash ADC structure, but with far less bits.

A single CA339 + 4 trimpots would give you five voltage levels, and take 4 bits on the logic analyzer.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 19, 2018, 05:22:57 pm
You can hook if a few analog comparators to diffetentiate between the required voltage levels. Something like a flash ADC structure, but with far less bits.

A single CA339 + 4 trimpots would give you five voltage levels, and take 4 bits on the logic analyzer.

Enviado de meu SM-N910C usando o Tapatalk

Hi,

Thanks for the idea, looks like ZeroPlus is doing the same in their commercial offering: https://www.thedebugstore.com/dso-lap-c-zeroplus.html (https://www.thedebugstore.com/dso-lap-c-zeroplus.html)

Fortunately the different voltages applied are not so complicated. Just VPP (PA.5) and VDD are set to different level when each programing step starts. A simple measurement with a scope is no problem. Since we can count the trigger pulses in logic analyzer (VPP low / high transitions) it is easy to setup the scope to ignore X trigger and we arrive at the desired programing step to measure / monitor the voltage.


JS


EDIT: Since I like the idea of using some bits of the logic analyzer to capture analog voltage so much, I will use a cheap STM32F072 board to do exactly this... 2 parallel ADC channels, output 2x8 bit, should only take an hour to implement :-)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 19, 2018, 08:14:20 pm
EDIT: Since I like the idea of using some bits of the logic analyzer to capture analog voltage so much, I will use a cheap STM32F072 board to do exactly this... 2 parallel ADC channels, output 2x8 bit, should only take an hour to implement :-)

A Padauk or Puolop would provide the ADC channels cheaper.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 21, 2018, 03:15:58 pm

A Padauk or Puolop would provide the ADC channels cheaper.

Philipp

This would be an excellent choice in the future. I also did not see the 100% identical "Puolop" brand before  8)

Right now I do not have the PFS173 with ADC und use the STM32F072 I have at hand (also not very expensive).


Capture analog values for logic analyzer using STM32F072:

Hardware:
I use STM32F072 on this little board (USD 2.80): https://item.taobao.com/item.htm?id=539758673887 (https://item.taobao.com/item.htm?id=539758673887)
(schematics: http://www.vcc-gnd.com/jikeliangpinstm32f072c8t6xuexibanziliao (http://www.vcc-gnd.com/jikeliangpinstm32f072c8t6xuexibanziliao) )

Mini ST-Link/V2 compatible device for uploading / debugging (USD 1.40): https://item.taobao.com/item.htm?id=560869168693 (https://item.taobao.com/item.htm?id=560869168693)

Software:

1. Use CubeMX software from ST and load the file "A2LASTM32.ioc"
    The project is configured to use 2 ADC channels in 8bit mode on PA0 and PA1 and use the complete GPIOB as 16 bit output (PB0-PB15).
    ADC is configured for continuous scan using DMA to write into a circular double buffer
    DMA will trigger interrupts + callbacks whenever first or second part of double buffer is complete

2. and click "Generate Code"
   (you can change code generator to your preferred IDE)

2. Open the generated code with your preferred IDE

3. Add the following code in the specified sections in "main.c" of the generated code:

    DMA callbacks combine the 2 ADC values into a 16 bit value and set GPIOB output (USER CODE 0, see below)

    ADC is calibrated and started in main (USER CODE 2, see below)

Code: [Select]
...

/* USER CODE BEGIN 0 */

//double buffer(2) * 32 bit  //  32 bit = (2 * 16 bit) // each adc value always takes 16 bit
static uint32_t adcDMABuffer[2];

//first part of double buffer complete
void HAL_ADC_ConvHalfCpltCallback(ADC_HandleTypeDef* AdcHandle) {
  //combine and output 2 adc values (8bit : 8bit) on GPIOB
  GPIOB->ODR = (adcDMABuffer[0] | (adcDMABuffer[0]>>8)) & 0xFFFF;
}

//second part of double buffer complete
void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* AdcHandle) {
  //combine and output 2 adc values (8bit : 8bit) on GPIOB
  GPIOB->ODR = (adcDMABuffer[1] | (adcDMABuffer[1]>>8)) & 0xFFFF;
}

/* USER CODE END 0 */


...


/* USER CODE BEGIN 2 */

HAL_ADCEx_Calibration_Start(&hadc);
HAL_ADC_Start_DMA(&hadc, (uint32_t*)adcDMABuffer, 2*2 );

/* USER CODE END 2 */

...

4. Compile it

5. Upload it using ST-Link/V2 (your IDE supports this for sure)



Was a nice experience. I just used the CubeMX configurator with the mouse and typed 7 lines of code (excluding comments).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 22, 2018, 03:02:22 pm
Hi,

I was trying to find out some info about the "BGTR" register which is defined in PFS154.INC and used by init code of PFS154 when I came across this:

"SONiX 8-Bit Micro-Controller"

I think I just found the initial IC designer which seem to have created the CPU core in 2004 or earlier (several years before PADAUK adapted it):

==> http://www.sonix.com.tw/list-en-1006 (http://www.sonix.com.tw/list-en-1006)

They also have flash versions:

==> http://www.sonix.com.tw/list-en-1001 (http://www.sonix.com.tw/list-en-1001)

More external files:

http://www.alldatasheet.com/view.jsp?Searchword=SN8P2722 (http://www.alldatasheet.com/view.jsp?Searchword=SN8P2722)
http://pdf1.alldatasheet.com/datasheet-pdf/view/110082/SONIX/SN8P2501A.html (http://pdf1.alldatasheet.com/datasheet-pdf/view/110082/SONIX/SN8P2501A.html)
...


The PADAUK IC versions seem to have small changes but we can learn a LOT from SONIX datasheets:

e.g.: P1.1/RST/VPP ... VPP: OTP 12.3V power input pin in programming mode

==> And a section mentioning "BandGap" near IHRC and ILRC (just like in PFS154.INC file)

So
IHRCR = Internal High speed R/C Register
ILRCR = Internal Low speed R/C Register
BGTR might be Band Gap Tuning Register


JS



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 22, 2018, 05:08:37 pm
Hi,

I was trying to find out some info about the "BGTR" register which is defined in PFS154.INC and used by init code of PFS154 when I came across this:

"SONiX 8-Bit Micro-Controller"

I think I just found the initial IC designer which seem to have created the CPU core in 2004 or earlier (several years before PADAUK adapted it):
[…]

That looks somewhat similar to, but still different from the Padauk devices. In particular, Padauk (and Puolop) have a stack in RAM. SONiX has a tiny fixed-size stack in separate memory (similar to low-end PIC devices). That makes Padauk / Puolop a better target for a C compiler.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 22, 2018, 05:11:04 pm
[…] I also did not see the 100% identical "Puolop" brand before  8)

Most of the range looks identical, down to the dates in the datasheet changelogs. But Padauk has some flash and 8-core devices, while Puolop hasn't. And there seem to be some Puolop 1-core OTP devices that do not have a Padauk equivalent.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 22, 2018, 10:27:30 pm
Hi,

I was trying to find out some info about the "BGTR" register which is defined in PFS154.INC and used by init code of PFS154 when I came across this:

"SONiX 8-Bit Micro-Controller"

I think I just found the initial IC designer which seem to have created the CPU core in 2004 or earlier (several years before PADAUK adapted it):
[…]

That looks somewhat similar to, but still different from the Padauk devices. In particular, Padauk (and Puolop) have a stack in RAM. SONiX has a tiny fixed-size stack in separate memory (similar to low-end PIC devices). That makes Padauk / Puolop a better target for a C compiler.

Philipp

Only somewhat similar? They share almost the same instruction set as the 16 bit PADAUK devices. There is a disassembler on github: https://github.com/vpelletier/dissn8  ... have a look yourself.

So I wonder why PADAUK binary PDK file is encrypted... want to hide the fact that main """inspiration""" came from SN8 core?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 23, 2018, 08:58:25 pm
Also found this site...

==> BE CAREFUL, NOT SURE IF THE TOOL IS LEGIT <==

http://www.mcusky.com/uasm/product_u51.asp (http://www.mcusky.com/uasm/product_u51.asp)


But they list PADAUK CPU and have a asm listing with valid 16 bit opcode bytes. (Looks like somebody in China was faster than us).

Somebody has setup handy to try (virtual machine, network restricted, ...)?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 24, 2018, 04:24:35 am
I added some eyes to a metal owl with a PMS150C:

https://www.youtube.com/watch?v=2q7OdzhhOmU (https://www.youtube.com/watch?v=2q7OdzhhOmU)

When the LED is dimmed, it needs about 300 uA, and when on about 2 mA. So the CR2032 batttery I used should last maybe at least a week.

The project file is attached. The PMS150C has no OTP ldtabl instruction, so I used a concept known from PICs: a lookup table with lots of "ret x" instructions, then calculating the address into this table, pushing it on stack and with a "ret" I jump into the table, returning the value I want. Needs some cycles, but not much space. Is there a better method? Getting the syntax right for the array etc. was not easy with the suboptimal documentation.

Interestingly with the ICE (in circuit emulator) it doesn't work, only when flashing the real chip. The ICE needs the switch-case part of the program. But I already contacted Padauk and they are looking into it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 24, 2018, 12:14:40 pm
Hi,

I think what you should use is the "PCADD" instructions. Your table lookup could look like this:

Code: [Select]
void LookUp_A(void)
{
    ADD A,1
    PCADD A
    RET 0x0F
    RET 0x1F
    RET 0x7F
    RET 0x00
}

...

    A = i;
    LookUp_A();
    tm2b = A;
...

One other important thing: PWM is NOT turned OFF when you write 0x00 to "tm2b".
The formula for duty cycle is: Duty of Output = [( K + 1 ) ÷ 256] × 100%  (you see the +1, oscilloscope also shows a small spike all the time)
So in order to save power you should turn off PWM instead.


JS

UPDATE:

I modified your program a bit to disable PWM output when there is "0" in the table. This should save some power.

Code: [Select]
void LookUp_A(void)
{
    //caller needs to make sure A is in range of 0-3
    ADD A,1
    PCADD A
    RET 0x0F
    RET 0x1F
    RET 0x7F
    RET 0x00
}

void FPPA0(void):stack=4
{
  .ADJUST_IC  SYSCLK=IHRC/32, IHRC=16MHz, VDD=3V, Bandgap=Off

  $ TM2S = 8BIT, /1, /1;             // 8-bit PWM, pre-scalar = 1, scalar = 1 (tm2s = 0b0_00_00000)

  while (1) {
    BYTE i = 0;
    while (1)
    {
      A = i;
      LookUp_A();
      if( 0==A )
        $ TM2C = STOP;
      else
      {
        TM2B = A;
        $ TM2C = SYSCLK, PA3, PWM;   // setup timer2 as pwm out: system clock (512kHz), output=PA3, PWM mode (tm2c = 0b0001_10_1_0)
      }
      i++;
      if (i == 4) break;
      .delay 40000;
    }
    .delay 1000000;
  }
}

To really save power the DELAYs should be done using a TIMER and STOPEXE mode. Then for sure your battery will last 3 months instead of 1 week.

UPDATE2:

I did several modifications to get a much better power efficiency:
- use ILRC/16 instead of IHRC
- disable IHRC
- use STOPEXE during the long 2 second sleep

Code: [Select]
void LookUp_A(void)                                  //caller needs to make sure A is in range of 0-3
{
  ADD A,1
  PCADD A
  RET 0x0F
  RET 0x1F
  RET 0x7F
  RET 0x00
}

void DeepSleep_2s(void)
{
  WORD sleep = 0;
  STT16 sleep

  INTRQ.T16 = 0;

  $ T16M = ILRC, /64, BIT11;                         //T16 clock source = ILRC (typ. 62 kHz on PMC150), / 64 => approx 1 kHz timer, 11BIT = 2048 => approx 2 seconds

  while( !INTRQ.T16 )                                //STOPEXE could be interrupted by multiple sources, we wait for T16 overflow here
    STOPEXE;

  $ T16M = STOP;
}

void FPPA0(void) : stack=2
{
  .ADJUST_IC  SYSCLK=ILRC (IHRC/16), IHRC=16MHz, VDD=3V, Bandgap=Off

#if _SYS (AT_ICE)
  $ CLKMD = ILRC/4, En_ILRC;                         // ICE does not support ILRC/16, so we use /4 instead
#else
  $ CLKMD = ILRC/16, En_ILRC;                        // use ILRC/16 as system clock (3.875kHz), turn off IHRC to save more power
#endif

  $ TM2S = 8BIT, /1, /1;                             // 8-bit PWM, pre-scalar = 1, scalar = 1 (tm2s = 0b0_00_00000)

  while (1)
  {
    BYTE i = 0;
    while (1)
    {
      A = i;
      LookUp_A();
      if( 0==A )
        $ TM2C = STOP;
      else
      {
        TM2B = A;
        $ TM2C = ILRC, PA3, PWM;             // setup timer2 as pwm out: clock ilrc (62kHz), output=PA3, PWM mode
      }
      i++;
      if (i == 4) break;
      .delay 300;
#if _SYS (AT_ICE)
      .delay 900;                                    // wait extra time since ICE clock is faster
#endif
    }
    DeepSleep_2s();
  }
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on December 24, 2018, 12:32:11 pm
You really need ADD A, 1?

Not sure about padauk, but other microcontroller always have PC pointing to the next instruction, so PCADD zero behaves like NOP.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 24, 2018, 12:34:38 pm
You really need ADD A, 1?

Not sure about padauk, but other microcontroller always have PC pointing to the next instruction, so PCADD zero behaves like NOP.

Enviado de meu SM-N910C usando o Tapatalk

Yes really need the +1 for PCADD. Otherwise my program was jumping into nowhere, crashing (I think it adds 256 in the case of A=0, will need to investigate)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 24, 2018, 05:08:54 pm
Thanks, good ideas. It is no problem for my program, but the pcadd wouldn't work with larger tables. But I could test for different 256 byte ranges, there is not much ROM anyway. PWM 0 with the short spike actually looks quite nice for the owl eyes in the dark, you can still see it slightly glowing.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 25, 2018, 05:15:54 am
I think the programmer is a bit rudimentary with all these jumpers, or maybe I'm doing something wrong? I managed to program the PMS150C parts with SOT-23-6 package, but it was a bit complicated.

I got an SOT-23-6 to DIP 14 adapter from Padauk, see attached images top.jpg and bottom.jpg. The pinout is odd:

signal -SOT-23-6 pin -DIP 14 pin
PA419
GND211
PA636
PA547
VDD54
PA368

When I tried to program it, it didn't work, because when I create a project for the PMS150C, the package in the PDK file is S08. In the program writer user manual (http://www.padauk.com.tw//upload/WRITERmanual/PDK5S-P-003-UM_EN_V006_20181030.pdf) on page 21 it looks like you can configure for each pin individually the signal function, like PA6 or VDD. But this didn't work.

So I did the procedure defined in chapter 5 for creating a "connecting board". On page 16 in the user manual you can see the pinout of JP7. The user manual is not very clear, but looks like each pin of JP7 is connected to the ZIF socket on top, except for 4 pins of the socket: The 8 bottom pins are connected to the socket, then there are 4 unconnected pins on the socket, and then the top 28 pins of JP7 are connected again to the socket.

I defined my own "connecting board", as defined  in chapter 5 with JP7. The way you do this is to connect the 8 lower pins to your specific pinout. I did this, connecting the signals PA3, PA4, PA5, PA6, VDD, and GND from the bottom 8 pins to my DIP 14 layout on the top side with jumper wires. You can see this in the image jp7.jpg. PA7 and PA0 doesn't need to be connected, which means a minimal programmer might need at most 6 pins, but maybe less. Then I added the pin definitions in the PRE file in the IDE, as explained on page 19 of the writer user manual:

Code: [Select]
.writer package 14, 4, 32, 8, 9, 7, 6, 32, 11, 0x0000, 0x0000, 0

I had some problems with the open/short tests, but using 0x0000 for mask1 and mask2 worked without problems, which disables all tests on all pins.

After looking again at the adapter layout, the pinout looks exactly like the pinout of the PFS154-S14 chip. Maybe this would have saved me some time with the jumper wires, because I would have needed to define just the right writer package instruction, and could then use one of the pre-defined jumpers for S14 packages. Anyone who did this for the SOT-23-6 parts?

Why I think the programmer is rudimentary: It looks like the with the jumpers JP1 to JP7, the fixed 8 programmer signals are routed to the ZIF socket pins and you have to manually short the pins on the jumpers. For some jumpers like JP2, you get this jumper block, which connects all pins in parallel and the routing is done by the PCB layout, but depending on the package, you have to set individual jumpers, like with JP5. If you have the right connector board, or if your pinout is one of the pre-defined pinouts to use the existing jumpers, it is no problem for production. Just plugin the right jumper, and you can program your chips. But would be much better if it could be configured all in software, without the need to manually change jumpers.

There are already a bunch of 4051 analog multiplexers on the programmer board, but I guess they are used only for the open/short test and maybe chip identification, not to route the programming signals. Probably this would be a problem anyway, if it needs higher power, like when routing VDD and GND. But shouldn't break the bank to add two individual transistors for each pin for switching VDD and GND if necessary, at least up to SOP16. But there are some low resistance multiplexers ICs available as well, which would reduce this to like 4 ICs instead of 32 transistors. Just as an idea, if someone is planning to build an easy to use, universal Padauk chip programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 01:46:15 pm
Hi,

I finally got the time to use a logic analyzer (ZeroPlus Logic Cube LAP-C322000) to capture the writing of a program on a PFS154.
...

Hello. I have downloaded the PDK and decrypted it, and got the following:
Code: [Select]
00000000: 70 00 00 2f 82 01 ed 3f 8b 01 ee 3f 9a 01 80 2f  p../...?...?.../
00000010: 9b 01 1c 2f 83 01 fe 3f ff 2a 54 30 ed 3f 81 0b  .../...?.*T0.?..
00000020: 91 1f 05 2f 80 0b d0 1a 13 30 90 1f 63 00 16 30  .../.....0..c..0
00000030: 80 11 16 30 90 1d d0 18 1b 30 01 2f 50 19 ff 2f  ...0.....0./P../
00000040: 01 0c 8b 01 81 0b d0 1a 23 30 50 1b 4f 30 04 2f  ........#0P.O0./
00000050: 88 01 d0 18 29 30 02 2f 82 01 04 13 05 13 6e 2f  ....)0./......n/
00000060: 82 0b 00 2f 83 0b 06 00 04 0b 07 00 05 08 84 15  .../............
00000070: 85 16 04 10 82 12 83 10 40 1a 33 30 90 1f d0 1a  ........@.30....
00000080: 3f 30 84 15 85 16 90 05 d0 18 44 30 50 19 3f 30  ?0........D0P.?0
00000090: 90 1d d0 1a 49 30 d0 18 4b 30 50 1b 2b 30 d0 18  ....I0..K0P.+0..
000000a0: 4f 30 50 1b 11 30 53 30 8b 01 d1 1e d0 1e 03 2f  O0P..0S0......./
000000b0: c1 0b 8a 2f c0 0b 56 2f 63 00 5c 30 c0 11 5c 30  .../..V/c.\0..\0
000000c0: c1 11 5c 30 d0 1c 03 2f c1 0b 8a 2f c0 0b 56 2f  ..\0.../.../..V/
000000d0: 63 00 68 30 c0 11 68 30 c1 11 68 30 56 30 ff 3f  c.h0..h0..h0V0.?
000000e0: ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f  .?.?.?.?.?.?.?.?
000000f0: ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f ff 3f  .?.?.?.?.?.?.?.?


I have also downloaded the text file and written a quick and dirty Python script (attached) for parsing PA6_ICPDA and PA3_ICPCK as SPI data and clock, respectively.

The output is:
Code: [Select]
      1009: 1010010110100101101001011010011000001010101000010
     55103: 1010010110100101101001011010011000011010101000010
     65685: 001111110111101111111111110000111111100000000000000001100011111110001000000000000111
     92201: 1010010110100101101001011010001100011010101000010
    112855: 0
    122857: 00
    132871: 0
    158597: 1010010110100101101001011010011001111010101000010
    737022: 1010010110100101101001011010011100001010101000010
    757693: 000000000001001111111111111111111111111111111111111111110011111110000000000000
    784240: 1010010110100101101001011010011000001010101000010
    820818: 1010010110100101101001011010011100001010101000010
    841488: 111111111111110000000000010011111111111111111111111111110011111110000000000000
    868054: 1010010110100101101001011010011000001010101000010
    904632: 1010010110100101101001011010011000001010101000010
    949230: 1010010110100101101001011010011000001010101000010
    969891: 00111111000001111111111111100011111100001011111111111110001111110001001111111111111100111111000110111111111111110011111100100111111111111111001111110010101111111111111100111111001100111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010011111111111111001111110101111111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011111111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000111111111111110011111111001111111111111111001111111101001111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100111111111111110011111111111111111111111111
   1004046: 1010010110100101101001011010011000011010101000010
   1589373: 1010010110100101101001011010011100011010101000010
   1620117: 000000011100001011110000000000000110000010111111111011010000000000000000000000000001100010111111111110111000000110011010101111100000000000000000100000000000000001100110111011110001110000000110000011111111111111100000000001000000000000101010111111111100000101010011111111101101001011100000010000000001100000000000011111100100011011110000010100101110000000011010110100000000000010000000000000110000000100110111111001000000000001100011110000000101100000000010100000000000010001100000001100000001011001110110010000011000110100000000000011000000000000110000000110111011110000000101100101010000101111111111110000000011100000000000001100000000010000011000101100101110000001011010110100000000000100000000000000110000001000110110110101000011000001001111101111000001000000000100100000000000000001100010000110001101000011000000101001101111000000100000000101000000000000000001100000100100110000010001001100000101101111011011100000000101100000000000001011100000101011110000000000101110000011000000000001100000000110000000000000001011000001000000000000011100100000000101010101100001000000000110100000000000010110100001010100000000010001001010000010010000100000110000000111000000000000011010010000001100000011001101111110010000011010110100000000000111100000000000110000001111110101011000010001011010000101000101100100000000001000000000000000011000110100001100000100010001100101010000110000001111110000001000100000000000011101100100000110101101000011000001001001011000110100000000001001000000000000110000010010110110110101000011000000101011011000110100000000001001100000000000110000010011110110110101000011000000010001110000010100110000001010000000000000000001100010110111101101000101111011010000101111000000110000001010100000000000001011110000011011111000101000101111000000101111010101100000001011000000000000000000011000111100000101110001000111000000110000010111000000001011100000000000010001110000011100000101110001110011010000101111000000110000001100000000000000001011110000011011111000101000101111000000101111010101100000001100100000000000000000011000111100000110100001000111000000110000011010000000001101000000000000010001110000011100000110100011000001010110111111111111110000001101100000000000
   1669266: 1010010110100101101001011010011100001010101000010
   1689953: 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001011111111110001111111010011111111100000000000
   1746862: 1010010110100101101001011010011000001010101000010
   1767523: 00111111000001111111111111100011111100001111111111111110001111110001011111111111111100111111000111111111111111110011111100100111111111111111001111110010101111111111111100111111001101111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010111111111111111001111110101101111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011111111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000110000101000010011111111001111111010101001001111111101011111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100000101111111110011111111111110001111111011
   1801641: 1010010110100101101001011010011000011010101000010
   1832399: 0000000000000000000011100000000000000000110111100000000000000000000100000011000001000000000000011111111111011010000000000010000000110001011000000000001011111111110111010000000000110000001100110100000000000011110111110000000100000000010000000011001101100000000001001101111000111000000000000101000000110000011000000000010110111111111111000000000001100101010111111110000000000110101000001010100100000000011101111111110110100000000001111001011100000011000000001000001111110010001100000000100010011110000010100000000010010001011100000001000000001001101101011010000000000000101001100000001001100000000010101011111100100001000000001011000000001100011100000000101111100000001011010000000011000010001100000000000000001100101000000010110100000000110100111011001000010000000011011011000110100001000000001110001000000011011100000000111011011110000000110000000011110011001010100001000000001111110111111111111000000001000000011000000000110000000100001000001100010110000000010001000101110000001000000001000110110101101000000000000100100010000001000110000000010010101101101010000100000001001101100000100111110000000100111101111000001001000000010100000000110001000100000001010010110001101000000000000101010010000001010010000000010101110111100000010100000001011000000011000001010000000101101010011000001000000000010111001001100000101000000001011111011110110111010000000110000001011100000101000000011000110111100000000000000001100100010111000001100000000110011000000000001100000000011010000101100000100000000001101010000000000011100000000110110001000000001010000000011011101010110000100000000001110000101101000010100000000111001010000000001001000000011101001001010000010100000001110110100001000001110000000111100011010010000001000000011110111000000110011100000001111100111111001000010000000111111011010110100001000000100000011000000111111100000010000010101011000010010000001000010010110100001011000000100001100010110010000100000010001000110001101000010000001000101010000010001000000000100011001100101010000100000010001110100000011111110000001001000011101100100001000000100100101101011010000100000010010100100000100100110000001001011011000110100001000000100110011000001001011100000010011010110110101000010000001001110010000001010111000000100111101100011010000100000010100001100000100111110000001010001011011010100001000000101001001000000010001100000010100110100000101001110000001010100000001100010111000000101010101111011010001100000010101100111101101000000000001010111101111000000111000000101100000101111000001100000010110011011111000101000000001011010001011110000000000000101101110111101010110000000010111000000000110001100000001011101110000010111000000000101111001000111000000000000010111111100000101110010000001100000010001110000011000000110000111000001011100100000011000100111001101000010000001100011101111000000111000000110010000101111000001100000011001011011111000101000000001100110001011110000000000000110011110111101010110000000011010000000000110001100000001101001110000011010000000000110101001000111000000000000011010111100000110100010000001101100010001110000011000000110110111000001101000100000011011101100000101011010000001101111111111111111111
   1890615: 1010010110100101101001011010011000011010101000010
   1935310: 1010010110100101101001011010011000001010101000010
   2004366: 1010010110100101101001011010011100011010101000010
   2035112: 000000011100001011110000000000000110000010111111111011010000000000000000000000000001100010111111111110111000000110011010101111100000000000000000100000000000000001100110111011110001110000000110000011111111111111100000000001000000000000101010111111111100000101010011111111101101001011100000010000000001100000000000011111100100011011110000010100101110000000011010110100000000000010000000000000110000000100110111111001000000000001100011110000000101100000000010100000000000010001100000001100000001011001110110010000011000110100000000000011000000000000110000000110111011110000000101100101010000101111111111110000000011100000000000001100000000010000011000101100101110000001011010110100000000000100000000000000110000001000110110110101000011000001001111101111000001000000000100100000000000000001100010000110001101000011000000101001101111000000100000000101000000000000000001100000100100110000010001001100000101101111011011100000000101100000000000001011100000101011110000000000101110000011000000000001100000000110000000000000001011000001000000000000011100100000000101010101100001000000000110100000000000010110100001010100000000010001001010000010010000100000110000000111000000000000011010010000001100000011001101111110010000011010110100000000000111100000000000110000001111110101011000010001011010000101000101100100000000001000000000000000011000110100001100000100010001100101010000110000001111110000001000100000000000011101100100000110101101000011000001001001011000110100000000001001000000000000110000010010110110110101000011000000101011011000110100000000001001100000000000110000010011110110110101000011000000010001110000010100110000001010000000000000000001100010110111101101000101111011010000101111000000110000001010100000000000001011110000011011111000101000101111000000101111010101100000001011000000000000000000011000111100000101110001000111000000110000010111000000001011100000000000010001110000011100000101110001110011010000101111000000110000001100000000000000001011110000011011111000101000101111000000101111010101100000001100100000000000000000011000111100000110100001000111000000110000011010000000001101000000000000010001110000011100000110100011000001010110111111111111110000001101100000000000
   2110976: 0
   2223667: 00
   2230308: 00
   2237010: 0
   2277626: 1101001010001110
   2301113: 0
   2304898: 11010010100011100
   2333060: 0
   2445751: 00
   2452389: 00
   2459091: 0
   2489632: 1101001010001110
   2523220: 0
   2527007: 11010010100011100
   2584511: 1010010110100101101001011010011100001010101000010
   2605196: 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001010000010110001111111010011111111100000000000
   2634228: 1010010110100101101001011010011000001010101000010
   2664969: 00111111000001111111111111100011111100001011111111111110001111110001001111111111111100111111000110111111111111110011111100100111111111111111001111110010101111111111111100111111001100111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010011111111111111001111110101101111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011011111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000110000101000010011111111001111111010101001001111111101011111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100000101000001010011111111111110001111111011
   2699086: 1010010110100101101001011010011000001010101000010
   2743782: 1010010110100101101001011010011100001010101000010
   2774546: 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001010000010110001111111010011111111100000000000


The transmission at 1620117 (which matches 1:1 that at 2035112) with 22 bit frames between 4-word blocks:
Code: [Select]
Exec.bin: 00000001110000 10111100000000 00000110000010 11111111101101                        00000110001011 11111111101110 00000110011010 10111110000000                        00000110011011 10111100011100 00000110000011 11111111111110                        10101011111111 11000001010100 11111111101101 00101110000001                        01111110010001 10111100000101 00101110000000 01101011010000                        11000000010011 01111110010000 00000001100011 11000000010110                        01000110000000 11000000010110 01110110010000 01100011010000                        11000000011011 10111100000001 01100101010000 10111111111111                        00110000000001 00000110001011 00101110000001 01101011010000                        11000000100011 01101101010000 11000001001111 10111100000100                        00000110001000 01100011010000 11000000101001 10111100000010                        00000110000010 01001100000100 01001100000101 10111101101110                        00101110000010 10111100000000 00101110000011 00000000000110                        00101100000100 00000000000111 00100000000101 01010110000100                        01011010000101 01000000000100 01001010000010 01000010000011                        01101001000000 11000000110011 01111110010000 01101011010000                        11000000111111 01010110000100 01011010000101 00010110010000                        01100011010000 11000001000100 01100101010000 11000000111111                        01110110010000 01101011010000 11000001001001 01100011010000                        11000001001011 01101101010000 11000000101011 01100011010000                        11000001001111 01101101010000 11000000010001 11000001010011                        00000110001011 01111011010001 01111011010000 10111100000011                        00101111000001 10111110001010 00101111000000 10111101010110                        00000001100011 11000001011100 01000111000000 11000001011100                        01000111000001 11000001011100 01110011010000 10111100000011                        00101111000001 10111110001010 00101111000000 10111101010110                        00000001100011 11000001101000 01000111000000 11000001101000                        01000111000001 11000001101000 11000001010110 11111111111111                       
 1620117: 00000001110000 10111100000000 00000110000010 11111111101101 0000000000000000000000 00000110001011 11111111101110 00000110011010 10111110000000 0000000000100000000000 00000110011011 10111100011100 00000110000011 11111111111110 0000000001000000000000 10101011111111 11000001010100 11111111101101 00101110000001 0000000001100000000000 01111110010001 10111100000101 00101110000000 01101011010000 0000000010000000000000 11000000010011 01111110010000 00000001100011 11000000010110 0000000010100000000000 01000110000000 11000000010110 01110110010000 01100011010000 0000000011000000000000 11000000011011 10111100000001 01100101010000 10111111111111 0000000011100000000000 00110000000001 00000110001011 00101110000001 01101011010000 0000000100000000000000 11000000100011 01101101010000 11000001001111 10111100000100 0000000100100000000000 00000110001000 01100011010000 11000000101001 10111100000010 0000000101000000000000 00000110000010 01001100000100 01001100000101 10111101101110 0000000101100000000000 00101110000010 10111100000000 00101110000011 00000000000110 0000000110000000000000 00101100000100 00000000000111 00100000000101 01010110000100 0000000110100000000000 01011010000101 01000000000100 01001010000010 01000010000011 0000000111000000000000 01101001000000 11000000110011 01111110010000 01101011010000 0000000111100000000000 11000000111111 01010110000100 01011010000101 00010110010000 0000001000000000000000 01100011010000 11000001000100 01100101010000 11000000111111 0000001000100000000000 01110110010000 01101011010000 11000001001001 01100011010000 0000001001000000000000 11000001001011 01101101010000 11000000101011 01100011010000 0000001001100000000000 11000001001111 01101101010000 11000000010001 11000001010011 0000001010000000000000 00000110001011 01111011010001 01111011010000 10111100000011 0000001010100000000000 00101111000001 10111110001010 00101111000000 10111101010110 0000001011000000000000 00000001100011 11000001011100 01000111000000 11000001011100 0000001011100000000000 01000111000001 11000001011100 01110011010000 10111100000011 0000001100000000000000 00101111000001 10111110001010 00101111000000 10111101010110 0000001100100000000000 00000001100011 11000001101000 01000111000000 11000001101000 0000001101000000000000 01000111000001 11000001101000 11000001010110 11111111111111 0000001101100000000000

It looks like it's loading 4 words, then sending the address to where it must be flashed to.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 02:10:31 pm
Hello @socram,

this is fantastic work :-)

Meanwhile I added two 8 bit channel which capture analog voltages as well.

I measured and normalized the analog conversion so the decimal decoded 8 bit value is voltage in 100mv step (e.g. 30 = 3.0V , 65 = 6.5V , ... )

I also found out that you can download and use the logic analyzer software without a real hardware in "DEMO-Mode"
Download: LAP-C V3.14.06 2018-11-19 : http://bd.zeroplus.com.tw/www/lac_s31406_all.zip (http://bd.zeroplus.com.tw/www/lac_s31406_all.zip)
==> Select "LAP-C32000" as demo device.

Now I can share the captures directly (much smaller size) and you still can export them to text ("File->Export->Waveform...").


I also did some more captures (I just pressed all buttons in Writer GUI which started an operation):

- PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_Program (erase,write,calibrate)

- PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_Verify

- PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_BlankCheck (was not blank, was programmed properly with SimpleBlink PDK before)

- PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_ReadSearch

NOTE:
Since the analog channel used a bit of the analyzer memory some captures are in chunks (pages). So when you see _P1, _P2, ... means they need to be stitched together (not sure where exactly need to stitch, maybe the 1% pre trigger is applied to the following pages as well and some values might be doubled)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 02:38:40 pm
I have improved a bit the Python script and now the logs are much clear. Instead of expecting a fixed time between transmissions, it uses the VDD signal to detect power cycling:
Code: [Select]
      1009       : 1010010110100101101001011010011000001010101000010
     55103   READ: 1010010110100101101001011010011000011010101000010 001111110111101111111111110000111111100000000000000001100011111110001000000000000111
     92201       : 1010010110100101101001011010001100011010101000010 0000
    158597       : 1010010110100101101001011010011001111010101000010
    737022       : 1010010110100101101001011010011100001010101000010 000000000001001111111111111111111111111111111111111111110011111110000000000000
    784240       : 1010010110100101101001011010011000001010101000010
    820818       : 1010010110100101101001011010011100001010101000010 111111111111110000000000010011111111111111111111111111110011111110000000000000
    868054       : 1010010110100101101001011010011000001010101000010
    904632       : 1010010110100101101001011010011000001010101000010
    949230       : 1010010110100101101001011010011000001010101000010 00111111000001111111111111100011111100001011111111111110001111110001001111111111111100111111000110111111111111110011111100100111111111111111001111110010101111111111111100111111001100111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010011111111111111001111110101111111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011111111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000111111111111110011111111001111111111111111001111111101001111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100111111111111110011111111111111111111111111
   1004046   READ: 1010010110100101101001011010011000011010101000010
   1589373  WRITE: 1010010110100101101001011010011100011010101000010 000000011100001011110000000000000110000010111111111011010000000000000000000000000001100010111111111110111000000110011010101111100000000000000000100000000000000001100110111011110001110000000110000011111111111111100000000001000000000000101010111111111100000101010011111111101101001011100000010000000001100000000000011111100100011011110000010100101110000000011010110100000000000010000000000000110000000100110111111001000000000001100011110000000101100000000010100000000000010001100000001100000001011001110110010000011000110100000000000011000000000000110000000110111011110000000101100101010000101111111111110000000011100000000000001100000000010000011000101100101110000001011010110100000000000100000000000000110000001000110110110101000011000001001111101111000001000000000100100000000000000001100010000110001101000011000000101001101111000000100000000101000000000000000001100000100100110000010001001100000101101111011011100000000101100000000000001011100000101011110000000000101110000011000000000001100000000110000000000000001011000001000000000000011100100000000101010101100001000000000110100000000000010110100001010100000000010001001010000010010000100000110000000111000000000000011010010000001100000011001101111110010000011010110100000000000111100000000000110000001111110101011000010001011010000101000101100100000000001000000000000000011000110100001100000100010001100101010000110000001111110000001000100000000000011101100100000110101101000011000001001001011000110100000000001001000000000000110000010010110110110101000011000000101011011000110100000000001001100000000000110000010011110110110101000011000000010001110000010100110000001010000000000000000001100010110111101101000101111011010000101111000000110000001010100000000000001011110000011011111000101000101111000000101111010101100000001011000000000000000000011000111100000101110001000111000000110000010111000000001011100000000000010001110000011100000101110001110011010000101111000000110000001100000000000000001011110000011011111000101000101111000000101111010101100000001100100000000000000000011000111100000110100001000111000000110000011010000000001101000000000000010001110000011100000110100011000001010110111111111111110000001101100000000000
   1669266       : 1010010110100101101001011010011100001010101000010 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001011111111110001111111010011111111100000000000
   1746862       : 1010010110100101101001011010011000001010101000010 00111111000001111111111111100011111100001111111111111110001111110001011111111111111100111111000111111111111111110011111100100111111111111111001111110010101111111111111100111111001101111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010111111111111111001111110101101111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011111111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000110000101000010011111111001111111010101001001111111101011111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100000101111111110011111111111110001111111011
   1801641   READ: 1010010110100101101001011010011000011010101000010 0000000000000000000011100000000000000000110111100000000000000000000100000011000001000000000000011111111111011010000000000010000000110001011000000000001011111111110111010000000000110000001100110100000000000011110111110000000100000000010000000011001101100000000001001101111000111000000000000101000000110000011000000000010110111111111111000000000001100101010111111110000000000110101000001010100100000000011101111111110110100000000001111001011100000011000000001000001111110010001100000000100010011110000010100000000010010001011100000001000000001001101101011010000000000000101001100000001001100000000010101011111100100001000000001011000000001100011100000000101111100000001011010000000011000010001100000000000000001100101000000010110100000000110100111011001000010000000011011011000110100001000000001110001000000011011100000000111011011110000000110000000011110011001010100001000000001111110111111111111000000001000000011000000000110000000100001000001100010110000000010001000101110000001000000001000110110101101000000000000100100010000001000110000000010010101101101010000100000001001101100000100111110000000100111101111000001001000000010100000000110001000100000001010010110001101000000000000101010010000001010010000000010101110111100000010100000001011000000011000001010000000101101010011000001000000000010111001001100000101000000001011111011110110111010000000110000001011100000101000000011000110111100000000000000001100100010111000001100000000110011000000000001100000000011010000101100000100000000001101010000000000011100000000110110001000000001010000000011011101010110000100000000001110000101101000010100000000111001010000000001001000000011101001001010000010100000001110110100001000001110000000111100011010010000001000000011110111000000110011100000001111100111111001000010000000111111011010110100001000000100000011000000111111100000010000010101011000010010000001000010010110100001011000000100001100010110010000100000010001000110001101000010000001000101010000010001000000000100011001100101010000100000010001110100000011111110000001001000011101100100001000000100100101101011010000100000010010100100000100100110000001001011011000110100001000000100110011000001001011100000010011010110110101000010000001001110010000001010111000000100111101100011010000100000010100001100000100111110000001010001011011010100001000000101001001000000010001100000010100110100000101001110000001010100000001100010111000000101010101111011010001100000010101100111101101000000000001010111101111000000111000000101100000101111000001100000010110011011111000101000000001011010001011110000000000000101101110111101010110000000010111000000000110001100000001011101110000010111000000000101111001000111000000000000010111111100000101110010000001100000010001110000011000000110000111000001011100100000011000100111001101000010000001100011101111000000111000000110010000101111000001100000011001011011111000101000000001100110001011110000000000000110011110111101010110000000011010000000000110001100000001101001110000011010000000000110101001000111000000000000011010111100000110100010000001101100010001110000011000000110110111000001101000100000011011101100000101011010000001101111111111111111111
   1890615   READ: 1010010110100101101001011010011000011010101000010
   1935310       : 1010010110100101101001011010011000001010101000010
   2004366  WRITE: 1010010110100101101001011010011100011010101000010 000000011100001011110000000000000110000010111111111011010000000000000000000000000001100010111111111110111000000110011010101111100000000000000000100000000000000001100110111011110001110000000110000011111111111111100000000001000000000000101010111111111100000101010011111111101101001011100000010000000001100000000000011111100100011011110000010100101110000000011010110100000000000010000000000000110000000100110111111001000000000001100011110000000101100000000010100000000000010001100000001100000001011001110110010000011000110100000000000011000000000000110000000110111011110000000101100101010000101111111111110000000011100000000000001100000000010000011000101100101110000001011010110100000000000100000000000000110000001000110110110101000011000001001111101111000001000000000100100000000000000001100010000110001101000011000000101001101111000000100000000101000000000000000001100000100100110000010001001100000101101111011011100000000101100000000000001011100000101011110000000000101110000011000000000001100000000110000000000000001011000001000000000000011100100000000101010101100001000000000110100000000000010110100001010100000000010001001010000010010000100000110000000111000000000000011010010000001100000011001101111110010000011010110100000000000111100000000000110000001111110101011000010001011010000101000101100100000000001000000000000000011000110100001100000100010001100101010000110000001111110000001000100000000000011101100100000110101101000011000001001001011000110100000000001001000000000000110000010010110110110101000011000000101011011000110100000000001001100000000000110000010011110110110101000011000000010001110000010100110000001010000000000000000001100010110111101101000101111011010000101111000000110000001010100000000000001011110000011011111000101000101111000000101111010101100000001011000000000000000000011000111100000101110001000111000000110000010111000000001011100000000000010001110000011100000101110001110011010000101111000000110000001100000000000000001011110000011011111000101000101111000000101111010101100000001100100000000000000000011000111100000110100001000111000000110000011010000000001101000000000000010001110000011100000110100011000001010110111111111111110000001101100000000000
   2110976       : 0000001101001010001110011010010100011100
   2333060       : 0000001101001010001110011010010100011100
   2584511       : 1010010110100101101001011010011100001010101000010 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001010000010110001111111010011111111100000000000
   2634228       : 1010010110100101101001011010011000001010101000010 00111111000001111111111111100011111100001011111111111110001111110001001111111111111100111111000110111111111111110011111100100111111111111111001111110010101111111111111100111111001100111111111111110011111100111011111111111111001111110100011111111111111100111111010010111111111111110011111101010011111111111111001111110101101111111111111100111111011001111111111111110011111101101000010100000011001111110111000001001111010100111111011110111111111111000011111110000000000000001000001111111000100000000000100100111111100101111111111111100011111110011011111111111110001111111010011111111111111100111111101011111111111111110011111110110111111111111111001111111011111111111111111100111111110000110000101000010011111111001111111010101001001111111101011111111111111100111111110111111111111111110011111111100011111111111111001111111110111111111111111100111111111100000101000001010011111111111110001111111011
   2699086       : 1010010110100101101001011010011000001010101000010
   2743782       : 1010010110100101101001011010011100001010101000010 111111111111110000101000000100001001111010011111111111100011111101100000000000000000000001000000000000010011111111111111111111111111110011111110000000000000011000010100001111110101010011111111111111111111111111110011111111000000000000111111111111111111111111111100001010000010110001111111010011111111100000000000

1589373 is now the program sequence (which also appears at 2004366 - they are still 1:1 identical, not sure why is it downloading the code twice).

I am downloading the software to export to TXT and run them through the script to find simmilarities, but it's still downloading (and will probably take a few hours - is this 2001?)

I wonder what's with 2110976 and 2333060, as they are not following the format of the rest - maybe it's something running on the microcontroller?

EDIT: It looks like 1801641 could be either read or verify:
Code: [Select]
COMMAND:
1010010110100101101001011010011000011010101000010

ADDRESS       DATA           ?
0000000000000 00000001110000 0
0000000000001 10111100000000 0
0000000000010 00000110000010 0
0000000000011 11111111101101 0
0000000000100 00000110001011 0
0000000000101 11111111101110 1
0000000000110 00000110011010 0
0000000000111 10111110000000 1
0000000001000 00000110011011 0
0000000001001 10111100011100 0
0000000001010 00000110000011 0
0000000001011 01111111111110 0
0000000001100 10101011111111 0
0000000001101 01000001010100 1
0000000001110 11111111101101 0
0000000001111 00101110000001 1
0000000010000 01111110010001 1
0000000010001 00111100000101 0
0000000010010 00101110000000 1
0000000010011 01101011010000 0
0000000010100 11000000010011 0
0000000010101 01111110010000 1
0000000010110 00000001100011 1
0000000010111 11000000010110 1
0000000011000 01000110000000 0
0000000011001 01000000010110 1
0000000011010 01110110010000 1
0000000011011 01100011010000 1
0000000011100 01000000011011 1
0000000011101 10111100000001 1
0000000011110 01100101010000 1
0000000011111 10111111111111 0
0000000100000 00110000000001 1
0000000100001 00000110001011 0
0000000100010 00101110000001 0
0000000100011 01101011010000 0
0000000100100 01000000100011 0
0000000100101 01101101010000 1
0000000100110 11000001001111 1
0000000100111 10111100000100 1
0000000101000 00000110001000 1
0000000101001 01100011010000 0
0000000101010 01000000101001 0
0000000101011 10111100000010 1
0000000101100 00000110000010 1
0000000101101 01001100000100 0
0000000101110 01001100000101 0
0000000101111 10111101101110 1
0000000110000 00101110000010 1
0000000110001 10111100000000 0
0000000110010 00101110000011 0
0000000110011 00000000000110 0
0000000110100 00101100000100 0
0000000110101 00000000000111 0
0000000110110 00100000000101 0
0000000110111 01010110000100 0
0000000111000 01011010000101 0
0000000111001 01000000000100 1
0000000111010 01001010000010 1
0000000111011 01000010000011 1
0000000111100 01101001000000 1
0000000111101 11000000110011 1
0000000111110 01111110010000 1
0000000111111 01101011010000 1
0000001000000 11000000111111 1
0000001000001 01010110000100 1
0000001000010 01011010000101 1
0000001000011 00010110010000 1
0000001000100 01100011010000 1
0000001000101 01000001000100 0
0000001000110 01100101010000 1
0000001000111 01000000111111 1
0000001001000 01110110010000 1
0000001001001 01101011010000 1
0000001001010 01000001001001 1
0000001001011 01100011010000 1
0000001001100 11000001001011 1
0000001001101 01101101010000 1
0000001001110 01000000101011 1
0000001001111 01100011010000 1
0000001010000 11000001001111 1
0000001010001 01101101010000 1
0000001010010 01000000010001 1
0000001010011 01000001010011 1
0000001010100 00000110001011 1
0000001010101 01111011010001 1
0000001010110 01111011010000 0
0000001010111 10111100000011 1
0000001011000 00101111000001 1
0000001011001 10111110001010 0
0000001011010 00101111000000 0
0000001011011 10111101010110 0
0000001011100 00000001100011 0
0000001011101 11000001011100 0
0000001011110 01000111000000 0
0000001011111 11000001011100 1
0000001100000 01000111000001 1
0000001100001 11000001011100 1
0000001100010 01110011010000 1
0000001100011 10111100000011 1
0000001100100 00101111000001 1
0000001100101 10111110001010 0
0000001100110 00101111000000 0
0000001100111 10111101010110 0
0000001101000 00000001100011 0
0000001101001 11000001101000 0
0000001101010 01000111000000 0
0000001101011 11000001101000 1
0000001101100 01000111000001 1
0000001101101 11000001101000 1
0000001101110 11000001010110 1
0000001101111 11111111111111 1


I am not sure what the last bit could be, but the "data" is 1:1 the binary code that had just been programmed previously in the flash.

EDIT2: If that is indeed READ, then 55103 would be also reading 1FFE 0003 0003 from address 0x7EF
Code: [Select]
COMMAND:
1010010110100101101001011010011000011010101000010

ADDRESS       DATA           ?
0011111101111 01111111111110 0
0011111110000 00000000000011 0
0011111110001 00000000000011 1
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 04:45:57 pm
I wonder what's with 2110976 and 2333060, as they are not following the format of the rest - maybe it's something running on the microcontroller?

This is calibration discussed earlier in this thread with full disassembly.

I am not sure what the last bit could be, but the "data" is 1:1 the binary code that had just been programmed previously in the flash.

In case of READ/VERIFY/... the direction of CLK and DAT need to change:
begin (sending command): WRITER output: CLK/DAT, IC = input
after command (receive data): WRITER disables output of CLK/DAT and switches to input, IC = output

During this transition it looks like a "CLK" is generated which is in fact ignored by both sides (both sides are switching input/output of CLK/DAT). Saw this during writing.

If there is no switch of modes in the read command it also might be a PARITY bit?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 05:30:35 pm
I am not sure. I had also thought of the parity bit, but it doesn't seem to make sense (for example, because it stays as 1 when one bit in the address or data is flipped). I had also tried sampling on the falling edge but again, it didn't make any sense.

Other files:

PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_BlankCheck.txt

Code: [Select]
      1207: FLASH_READ_1
            No data (dummy read)

     27385: FLASH_READ_2
            No data (dummy read)

     72043: FLASH_READ_2

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 1FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0025 0
            07F1 0025 1
            07F2 3FFF 0
            07F3 1FFF 0
            07F4 3FFF 1
            07F5 1FFF 1
            07F6 3FFF 1
            07F7 1FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

    126900: FLASH_READ_2
            No data (dummy read)



PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_Program_P1.txt

Code: [Select]
      1209: FLASH_READ_B
            No data (dummy read)

     55304: FLASH_READ_B

            ADDR DATA ?
            -----------
            07EF 1FFE 0
            07F0 0021 0
            07F1 0021 1

    102483: ??? (1010010110100101101001011010001100001010101000010)

    178976: ??? (1010010110100101101001011010011001111010101000010)

    747185: FLASH_WRITE

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0022 3FFF 3FFF 3FFF


    794400: FLASH_READ_A
            No data (dummy read)

    830958: ??? (1010010110100101101001011010011100001010101000010)

    878196: FLASH_READ_B
            No data (dummy read)

    914794: FLASH_READ_A
            No data (dummy read)

    959391: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 3FFF 1
            07E6 3FFF 1
            07E7 3FFF 1
            07E8 3FFF 1
            07E9 3FFF 1
            07EA 3FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0022 0
            07F1 0022 1
            07F2 3FFF 0
            07F3 1FFF 0
            07F4 3FFF 1
            07F5 1FFF 1
            07F6 1FFF 1
            07F7 1FFF 1
            07F8 3FFF 1
            07F9 1FFF 1
            07FA 1FFF 1
            07FB 1FFF 1
            07FC 3FFF 1
            07FD 1FFF 1
            07FE 3FFF 1
            07FF 3FFF 1

   1014210: FLASH_READ_B
            No data (dummy read)


PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck_Bus_AVDD_Verify

Code: [Select]
      1209: FLASH_READ_B
            No data (dummy read)

     27386: FLASH_READ_B
            No data (dummy read)

     72043: FLASH_READ_A

            ADDR DATA ?
            -----------
            07E0 1FFF 0
            07E1 1FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 3FFF 1
            07E6 1FFF 1
            07E7 3FFF 1
            07E8 1FFF 1
            07E9 3FFF 1
            07EA 1FFF 1
            07EB 3FFF 1
            07EC 1FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 001F 0
            07F1 001F 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 3FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

    136979: FLASH_READ_A
            No data (dummy read)

    695006: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 1FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 001F 0
            07F1 001F 1
            07F2 3FFF 0
            07F3 1FFF 0
            07F4 3FFF 1
            07F5 1FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

    749723: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 3FFF 1
            07E7 3FFF 1
            07E8 3FFF 1
            07E9 3FFF 1
            07EA 3FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 001F 0
            07F1 001F 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 1FFF 1
            07F5 3FFF 1
            07F6 1FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

    804580: FLASH_READ_A

            ADDR DATA ?
            -----------
            0000 0070 0
            0001 2F00 0
            0002 0182 0
            0003 3FED 0
            0004 018B 0
            0005 3FEE 1
            0006 019A 0
            0007 2F80 1
            0008 019B 0
            0009 2F1C 0
            000A 0183 0
            000B 3FFE 0
            000C 0AFF 0
            000D 3054 1
            000E 1FED 0
            000F 0B81 1
            0010 1F91 1
            0011 2F05 0
            0012 0B80 1
            0013 1AD0 0
            0014 3013 0
            0015 1F90 1
            0016 0063 1
            0017 3016 1
            0018 1180 0
            0019 3016 1
            001A 1D90 1
            001B 18D0 1
            001C 301B 1
            001D 2F01 1
            001E 1950 1
            001F 2FFF 0
            0020 0C01 1
            0021 018B 0
            0022 0B81 0
            0023 1AD0 0
            0024 3023 0
            0025 1B50 1
            0026 304F 1
            0027 2F04 1
            0028 0188 1
            0029 18D0 0
            002A 3029 0
            002B 0F02 1
            002C 0182 1
            002D 1304 0
            002E 1305 0
            002F 0F6E 1
            0030 0B82 1
            0031 0F00 0
            0032 0B83 0
            0033 0006 0
            0034 0B04 0
            0035 0007 0
            0036 0805 0
            0037 1584 0
            0038 1685 0
            0039 1004 1
            003A 1282 1
            003B 1083 1
            003C 1A40 1
            003D 3033 1
            003E 1F90 1
            003F 1AD0 1
            0040 303F 1
            0041 1584 1
            0042 1685 1
            0043 0590 1
            0044 18D0 1
            0045 3044 0
            0046 1950 1
            0047 303F 1
            0048 1D90 1
            0049 1AD0 1
            004A 3049 1
            004B 18D0 1
            004C 104B 1
            004D 1B50 1
            004E 302B 1
            004F 18D0 1
            0050 104F 1
            0051 1B50 1
            0052 3011 1
            0053 3053 1
            0054 018B 1
            0055 1ED1 1
            0056 1ED0 0
            0057 2F03 1
            0058 0BC1 1
            0059 2F8A 0
            005A 0BC0 0
            005B 2F56 0
            005C 0063 0
            005D 305C 0
            005E 11C0 0
            005F 305C 1
            0060 11C1 1
            0061 305C 1
            0062 1CD0 1
            0063 2F03 1
            0064 0BC1 1
            0065 2F8A 0
            0066 0BC0 0
            0067 2F56 0
            0068 0063 0
            0069 1068 0
            006A 11C0 0
            006B 3068 1
            006C 11C1 1
            006D 3068 1
            006E 1056 1
            006F 1FFF 1
            0070 3FFF 1
            0071 1FFF 1
            0072 3FFF 1
            0073 1FFF 1
            0074 3FFF 1
            0075 1FFF 1
            0076 3FFF 1
            0077 1FFF 1
            0078 3FFF 1
            0079 1FFF 1
            007A 3FFF 1
            007B 1FFF 1
            007C 3FFF 1
            007D 1FFF 1
            007E 3FFF 1
            007F 3FFF 1
            0080 1FFF 1
            0081 3FFF 1
            0082 1FFF 1
            0083 3FFF 1
            0084 1FFF 1
            0085 3FFF 1
            0086 1FFF 1
            0087 3FFF 1
            0088 1FFF 1
            0089 3FFF 1
            008A 3FFF 1
            008B 3FFF 1
            008C 1FFF 1
            008D 3FFF 1
            008E 3FFF 1
            008F 3FFF 1
            0090 1FFF 1
            0091 3FFF 1
            0092 3FFF 1
            0093 3FFF 1
            0094 1FFF 1
            0095 3FFF 1
            0096 3FFF 1
            0097 3FFF 1
            0098 3FFF 1
            0099 3FFF 1
            009A 3FFF 1
            009B 3FFF 1
            009C 3FFF 1
            009D 3FFF 1
            009E 3FFF 1
            009F 3FFF 1
            00A0 3FFF 1
            00A1 3FFF 1
            00A2 3FFF 1
            00A3 3FFF 1
            00A4 3FFF 1
            00A5 3FFF 1
            00A6 3FFF 1
            00A7 3FFF 1
            00A8 3FFF 1
            00A9 3FFF 1
            00AA 3FFF 1
            00AB 3FFF 1
            00AC 3FFF 1
            00AD 3FFF 1
            00AE 3FFF 1
            00AF 1FFF 1
            00B0 3FFF 1
            00B1 1FFF 1
            00B2 1FFF 1
            00B3 1FFF 1
            00B4 3FFF 1
            00B5 1FFF 1
            00B6 1FFF 1
            00B7 1FFF 1
            00B8 3FFF 1
            00B9 1FFF 1
            00BA 1FFF 1
            00BB 1FFF 1
            00BC 3FFF 1
            00BD 1FFF 1
            00BE 1FFF 1
            00BF 3FFF 1
            00C0 1FFF 1
            00C1 1FFF 1
            00C2 1FFF 1
            00C3 3FFF 1
            00C4 1FFF 1
            00C5 3FFF 1
            00C6 1FFF 1
            00C7 3FFF 1
            00C8 1FFF 1
            00C9 3FFF 1
            00CA 3FFF 1
            00CB 3FFF 1
            00CC 1FFF 1
            00CD 3FFF 1
            00CE 3FFF 1
            00CF 3FFF 1
            00D0 1FFF 1
            00D1 3FFF 1
            00D2 3FFF 1
            00D3 3FFF 1
            00D4 1FFF 1
            00D5 3FFF 1
            00D6 3FFF 1
            00D7 3FFF 1
            00D8 1FFF 1
            00D9 3FFF 1
            00DA 3FFF 1
            00DB 3FFF 1
            00DC 3FFF 1
            00DD 3FFF 1
            00DE 3FFF 1
            00DF 3FFF 1
            00E0 3FFF 1
            00E1 3FFF 1
            00E2 3FFF 1
            00E3 3FFF 1
            00E4 3FFF 1
            00E5 3FFF 1
            00E6 3FFF 1
            00E7 3FFF 1
            00E8 3FFF 1
            00E9 3FFF 1
            00EA 3FFF 1
            00EB 3FFF 1
            00EC 3FFF 1
            00ED 3FFF 1
            00EE 3FFF 1
            00EF 3FFF 1
            00F0 3FFF 1
            00F1 1FFF 1
            00F2 1FFF 1
            00F3 1FFF 1
            00F4 3FFF 1
            00F5 1FFF 1
            00F6 1FFF 1
            00F7 1FFF 1
            00F8 3FFF 1
            00F9 1FFF 1
            00FA 1FFF 1
            00FB 1FFF 1
            00FC 3FFF 1
            00FD 1FFF 1
            00FE 1FFF 1
            00FF 1FFF 1
            0100 1FFF 1
            0101 1FFF 1
            0102 1FFF 1
            0103 1FFF 1
            0104 1FFF 1
            0105 3FFF 1
            0106 1FFF 1
            0107 3FFF 1
            0108 3FFF 1
            0109 3FFF 1
            010A 3FFF 1
            010B 3FFF 1
            010C 1FFF 1
            010D 3FFF 1
            010E 3FFF 1
            010F 3FFF 1
            0110 1FFF 1
            0111 3FFF 1
            0112 3FFF 1
            0113 3FFF 1
            0114 1FFF 1
            0115 3FFF 1
            0116 3FFF 1
            0117 3FFF 1
            0118 1FFF 1
            0119 3FFF 1
            011A 3FFF 1
            011B 3FFF 1
            011C 3FFF 1
            011D 3FFF 1
            011E 3FFF 1
            011F 3FFF 1
            0120 3FFF 1
            0121 3FFF 1
            0122 3FFF 1
            0123 3FFF 1
            0124 3FFF 1
            0125 3FFF 1
            0126 3FFF 1
            0127 3FFF 1
            0128 3FFF 1
            0129 3FFF 1
            012A 3FFF 1
            012B 3FFF 1
            012C 3FFF 1
            012D 3FFF 1
            012E 3FFF 1
            012F 3FFF 1
            0130 3FFF 1
            0131 3FFF 1
            0132 3FFF 1
            0133 3FFF 1
            0134 3FFF 1
            0135 1FFF 1
            0136 1FFF 1
            0137 1FFF 1
            0138 3FFF 1
            0139 1FFF 1
            013A 1FFF 1
            013B 1FFF 1
            013C 3FFF 1
            013D 1FFF 1
            013E 1FFF 1
            013F 1FFF 1
            0140 3FFF 1
            0141 1FFF 1
            0142 1FFF 1
            0143 1FFF 1
            0144 1FFF 1
            0145 1FFF 1
            0146 1FFF 1
            0147 1FFF 1
            0148 3FFF 1
            0149 3FFF 1
            014A 3FFF 1
            014B 3FFF 1
            014C 3FFF 1
            014D 3FFF 1
            014E 3FFF 1
            014F 3FFF 1
            0150 1FFF 1
            0151 3FFF 1
            0152 3FFF 1
            0153 3FFF 1
            0154 1FFF 1
            0155 3FFF 1
            0156 3FFF 1
            0157 3FFF 1
            0158 1FFF 1
            0159 3FFF 1
            015A 3FFF 1
            015B 3FFF 1
            015C 1FFF 1
            015D 3FFF 1
            015E 3FFF 1
            015F 3FFF 1
            0160 3FFF 1
            0161 3FFF 1
            0162 3FFF 1
            0163 3FFF 1
            0164 3FFF 1
            0165 3FFF 1
            0166 3FFF 1
            0167 3FFF 1
            0168 3FFF 1
            0169 3FFF 1
            016A 3FFF 1
            016B 3FFF 1
            016C 3FFF 1
            016D 3FFF 1
            016E 3FFF 1
            016F 3FFF 1
            0170 3FFF 1
            0171 3FFF 1
            0172 3FFF 1
            0173 3FFF 1
            0174 3FFF 1
            0175 3FFF 1
            0176 3FFF 1
            0177 1FFF 1
            0178 3FFF 1
            0179 1FFF 1
            017A 1FFF 1
            017B 1FFF 1
            017C 3FFF 1
            017D 1FFF 1
            017E 1FFF 1
            017F 1FFF 1
            0180 3FFF 1
            0181 1FFF 1
            0182 3FFF 1
            0183 1FFF 1
            0184 3FFF 1
            0185 1FFF 1
            0186 1FFF 1
            0187 1FFF 1
            0188 3FFF 1
            0189 3FFF 1
            018A 3FFF 1
            018B 3FFF 1
            018C 3FFF 1
            018D 3FFF 1
            018E 3FFF 1
            018F 3FFF 1
            0190 1FFF 1
            0191 3FFF 1
            0192 3FFF 1
            0193 3FFF 1
            0194 1FFF 1
            0195 3FFF 1
            0196 3FFF 1
            0197 3FFF 1
            0198 1FFF 1
            0199 3FFF 1
            019A 3FFF 1
            019B 3FFF 1
            019C 1FFF 1
            019D 3FFF 1
            019E 3FFF 1
            019F 3FFF 1
            01A0 1FFF 1
            01A1 3FFF 1
            01A2 3FFF 1
            01A3 3FFF 1
            01A4 3FFF 1
            01A5 3FFF 1
            01A6 3FFF 1
            01A7 3FFF 1
            01A8 3FFF 1
            01A9 3FFF 1
            01AA 3FFF 1
            01AB 3FFF 1
            01AC 3FFF 1
            01AD 3FFF 1
            01AE 3FFF 1
            01AF 3FFF 1
            01B0 3FFF 1
            01B1 3FFF 1
            01B2 3FFF 1
            01B3 3FFF 1
            01B4 3FFF 1
            01B5 3FFF 1
            01B6 3FFF 1
            01B7 3FFF 1
            01B8 3FFF 1
            01B9 1FFF 1
            01BA 1FFF 1
            01BB 1FFF 1
            01BC 3FFF 1
            01BD 1FFF 1
            01BE 1FFF 1
            01BF 1FFF 1
            01C0 3FFF 1
            01C1 1FFF 1
            01C2 3FFF 1
            01C3 1FFF 1
            01C4 3FFF 1
            01C5 1FFF 1
            01C6 3FFF 1
            01C7 1FFF 1
            01C8 3FFF 1
            01C9 1FFF 1
            01CA 3FFF 1
            01CB 3FFF 1
            01CC 3FFF 1
            01CD 3FFF 1
            01CE 3FFF 1
            01CF 3FFF 1
            01D0 3FFF 1
            01D1 3FFF 1
            01D2 3FFF 1
            01D3 3FFF 1
            01D4 1FFF 1
            01D5 3FFF 1
            01D6 3FFF 1
            01D7 3FFF 1
            01D8 1FFF 1
            01D9 3FFF 1
            01DA 3FFF 1
            01DB 3FFF 1
            01DC 1FFF 1
            01DD 3FFF 1
            01DE 3FFF 1
            01DF 3FFF 1
            01E0 1FFF 1
            01E1 3FFF 1
            01E2 3FFF 1
            01E3 3FFF 1
            01E4 3FFF 1
            01E5 3FFF 1
            01E6 3FFF 1
            01E7 3FFF 1
            01E8 3FFF 1
            01E9 3FFF 1
            01EA 3FFF 1
            01EB 3FFF 1
            01EC 3FFF 1
            01ED 3FFF 1
            01EE 3FFF 1
            01EF 3FFF 1
            01F0 3FFF 1
            01F1 3FFF 1
            01F2 3FFF 1
            01F3 3FFF 1
            01F4 3FFF 1
            01F5 3FFF 1
            01F6 3FFF 1
            01F7 3FFF 1
            01F8 3FFF 1
            01F9 3FFF 1
            01FA 3FFF 1
            01FB 3FFF 1
            01FC 3FFF 1
            01FD 1FFF 1
            01FE 1FFF 1
            01FF 1FFF 1
            0200 3FFF 1
            0201 1FFF 1
            0202 3FFF 1
            0203 1FFF 1
            0204 3FFF 1
            0205 1FFF 1
            0206 3FFF 1
            0207 1FFF 1
            0208 3FFF 1
            0209 1FFF 1
            020A 1FFF 1
            020B 1FFF 1
            020C 3FFF 1
            020D 3FFF 1
            020E 3FFF 1
            020F 3FFF 1
            0210 3FFF 1
            0211 3FFF 1
            0212 3FFF 1
            0213 3FFF 1
            0214 3FFF 1
            0215 3FFF 1
            0216 3FFF 1
            0217 3FFF 1
            0218 1FFF 1
            0219 3FFF 1
            021A 3FFF 1
            021B 3FFF 1
            021C 1FFF 1
            021D 3FFF 1
            021E 3FFF 1
            021F 3FFF 1
            0220 1FFF 1
            0221 3FFF 1
            0222 3FFF 1
            0223 3FFF 1
            0224 1FFF 1
            0225 3FFF 1
            0226 3FFF 1
            0227 3FFF 1
            0228 3FFF 1
            0229 3FFF 1
            022A 3FFF 1
            022B 3FFF 1
            022C 3FFF 1
            022D 3FFF 1
            022E 3FFF 1
            022F 3FFF 1
            0230 3FFF 1
            0231 3FFF 1
            0232 3FFF 1
            0233 3FFF 1
            0234 3FFF 1
            0235 3FFF 1
            0236 3FFF 1
            0237 3FFF 1
            0238 3FFF 1
            0239 3FFF 1
            023A 3FFF 1
            023B 3FFF 1
            023C 3FFF 1
            023D 3FFF 1
            023E 3FFF 1
            023F 1FFF 1
            0240 3FFF 1
            0241 3FFF 1
            0242 3FFF 1
            0243 1FFF 1
            0244 3FFF 1
            0245 1FFF 1
            0246 3FFF 1
            0247 1FFF 1
            0248 3FFF 1
            0249 1FFF 1
            024A 1FFF 1
            024B 1FFF 1
            024C 3FFF 1
            024D 1FFF 1
            024E 1FFF 1
            024F 1FFF 1
            0250 3FFF 1
            0251 3FFF 1
            0252 3FFF 1
            0253 3FFF 1
            0254 3FFF 1
            0255 3FFF 1
            0256 3FFF 1
            0257 3FFF 1
            0258 1FFF 1
            0259 3FFF 1
            025A 3FFF 1
            025B 3FFF 1
            025C 1FFF 1
            025D 3FFF 1
            025E 3FFF 1
            025F 3FFF 1
            0260 1FFF 1
            0261 3FFF 1
            0262 3FFF 1
            0263 3FFF 1
            0264 1FFF 1
            0265 3FFF 1
            0266 3FFF 1
            0267 3FFF 1
            0268 1FFF 1
            0269 3FFF 1
            026A 3FFF 1
            026B 3FFF 1
            026C 3FFF 1
            026D 3FFF 1
            026E 3FFF 1
            026F 3FFF 1
            0270 3FFF 1
            0271 3FFF 1
            0272 3FFF 1
            0273 3FFF 1
            0274 3FFF 1
            0275 3FFF 1
            0276 3FFF 1
            0277 3FFF 1
            0278 3FFF 1
            0279 3FFF 1
            027A 3FFF 1
            027B 3FFF 1
            027C 3FFF 1
            027D 3FFF 1
            027E 3FFF 1
            027F 3FFF 1
            0280 3FFF 1
            0281 3FFF 1
            0282 3FFF 1
            0283 3FFF 1
            0284 3FFF 1
            0285 1FFF 1
            0286 3FFF 1
            0287 1FFF 1
            0288 3FFF 1
            0289 1FFF 1
            028A 1FFF 1
            028B 1FFF 1
            028C 3FFF 1
            028D 1FFF 1
            028E 1FFF 1
            028F 1FFF 1
            0290 3FFF 1
            0291 1FFF 1
            0292 1FFF 1
            0293 3FFF 1
            0294 3FFF 1
            0295 3FFF 1
            0296 3FFF 1
            0297 3FFF 1
            0298 3FFF 1
            0299 3FFF 1
            029A 3FFF 1
            029B 3FFF 1
            029C 1FFF 1
            029D 3FFF 1
            029E 3FFF 1
            029F 3FFF 1
            02A0 1FFF 1
            02A1 3FFF 1
            02A2 3FFF 1
            02A3 3FFF 1
            02A4 1FFF 1
            02A5 3FFF 1
            02A6 3FFF 1
            02A7 3FFF 1
            02A8 1FFF 1
            02A9 3FFF 1
            02AA 3FFF 1
            02AB 3FFF 1
            02AC 3FFF 1
            02AD 3FFF 1
            02AE 3FFF 1
            02AF 3FFF 1
            02B0 3FFF 1
            02B1 3FFF 1
            02B2 3FFF 1
            02B3 3FFF 1
            02B4 3FFF 1
            02B5 3FFF 1
            02B6 3FFF 1
            02B7 3FFF 1
            02B8 3FFF 1
            02B9 3FFF 1
            02BA 3FFF 1
            02BB 3FFF 1
            02BC 3FFF 1
            02BD 3FFF 1
            02BE 3FFF 1
            02BF 3FFF 1
            02C0 3FFF 1
            02C1 3FFF 1
            02C2 3FFF 1
            02C3 3FFF 1
            02C4 3FFF 1
            02C5 3FFF 1
            02C6 3FFF 1
            02C7 1FFF 1
            02C8 3FFF 1
            02C9 1FFF 1
            02CA 1FFF 1
            02CB 1FFF 1
            02CC 3FFF 1
            02CD 1FFF 1
            02CE 1FFF 1
            02CF 1FFF 1
            02D0 3FFF 1
            02D1 1FFF 1
            02D2 1FFF 1
            02D3 1FFF 1
            02D4 3FFF 1
            02D5 3FFF 1
            02D6 3FFF 1
            02D7 3FFF 1
            02D8 3FFF 1
            02D9 3FFF 1
            02DA 3FFF 1
            02DB 3FFF 1
            02DC 3FFF 1
            02DD 3FFF 1
            02DE 3FFF 1
            02DF 3FFF 1
            02E0 1FFF 1
            02E1 3FFF 1
            02E2 3FFF 1
            02E3 3FFF 1
            02E4 1FFF 1
            02E5 3FFF 1
            02E6 3FFF 1
            02E7 3FFF 1
            02E8 1FFF 1
            02E9 3FFF 1
            02EA 3FFF 1
            02EB 3FFF 1
            02EC 1FFF 1
            02ED 3FFF 1
            02EE 3FFF 1
            02EF 3FFF 1
            02F0 3FFF 1
            02F1 3FFF 1
            02F2 3FFF 1
            02F3 3FFF 1
            02F4 3FFF 1
            02F5 3FFF 1
            02F6 3FFF 1
            02F7 3FFF 1
            02F8 3FFF 1
            02F9 3FFF 1
            02FA 3FFF 1
            02FB 3FFF 1
            02FC 3FFF 1
            02FD 3FFF 1
            02FE 3FFF 1
            02FF 3FFF 1
            0300 3FFF 1
            0301 3FFF 1
            0302 3FFF 1
            0303 3FFF 1
            0304 3FFF 1
            0305 3FFF 1
            0306 3FFF 1
            0307 3FFF 1
            0308 3FFF 1
            0309 1FFF 1
            030A 1FFF 1
            030B 1FFF 1
            030C 3FFF 1
            030D 1FFF 1
            030E 1FFF 1
            030F 1FFF 1
            0310 3FFF 1
            0311 1FFF 1
            0312 1FFF 1
            0313 1FFF 1
            0314 3FFF 1
            0315 1FFF 1
            0316 1FFF 1
            0317 1FFF 1
            0318 3FFF 1
            0319 3FFF 1
            031A 3FFF 1
            031B 3FFF 1
            031C 3FFF 1
            031D 3FFF 1
            031E 3FFF 1
            031F 3FFF 1
            0320 1FFF 1
            0321 3FFF 1
            0322 3FFF 1
            0323 3FFF 1
            0324 1FFF 1
            0325 3FFF 1
            0326 3FFF 1
            0327 3FFF 1
            0328 1FFF 1
            0329 3FFF 1
            032A 3FFF 1
            032B 3FFF 1
            032C 1FFF 1
            032D 3FFF 1
            032E 3FFF 1
            032F 3FFF 1
            0330 1FFF 1
            0331 3FFF 1
            0332 3FFF 1
            0333 3FFF 1
            0334 3FFF 1
            0335 3FFF 1
            0336 3FFF 1


EDIT: Improved dumps with automatic decoding script.

So far:

I have no idea what's the difference between the two flash reads, but they at least use exactly the same output format, and they both seem to be used interchangeably.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 06:50:41 pm
There seems to be two Flash read commands and two Flash write commands - why? I have absolutely no idea.

Parsing again the first shared .txt file, one gets now:

PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck.txt

Code: [Select]
      1009: FLASH_READ_B
            No data (dummy read)

     55103: FLASH_READ_A

            ADDR DATA ?
            -----------
            07EF 1FFE 0
            07F0 0003 0
            07F1 0003 1

     92201: ??? (1010010110100101101001011010001100011010101000010)

    158597: ??? (1010010110100101101001011010011001111010101000010)

    737022: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0004 3FFF 3FFF 3FFF


    784240: FLASH_READ_B
            No data (dummy read)

    820818: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 3FFF 0004 3FFF 3FFF


    868054: FLASH_READ_B
            No data (dummy read)

    904632: FLASH_READ_B
            No data (dummy read)

    949230: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0004 0
            07F1 0004 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1FFF 1
            07F9 3FFF 1
            07FA 1FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 1FFF 1
            07FF 3FFF 1

   1004046: FLASH_READ_A
            No data (dummy read)

   1589373: FLASH_WRITE_A

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            0000 0070 2F00 0182 3FED
            0004 018B 3FEE 019A 2F80
            0008 019B 2F1C 0183 3FFE
            000C 2AFF 3054 3FED 0B81
            0010 1F91 2F05 0B80 1AD0
            0014 3013 1F90 0063 3016
            0018 1180 3016 1D90 18D0
            001C 301B 2F01 1950 2FFF
            0020 0C01 018B 0B81 1AD0
            0024 3023 1B50 304F 2F04
            0028 0188 18D0 3029 2F02
            002C 0182 1304 1305 2F6E
            0030 0B82 2F00 0B83 0006
            0034 0B04 0007 0805 1584
            0038 1685 1004 1282 1083
            003C 1A40 3033 1F90 1AD0
            0040 303F 1584 1685 0590
            0044 18D0 3044 1950 303F
            0048 1D90 1AD0 3049 18D0
            004C 304B 1B50 302B 18D0
            0050 304F 1B50 3011 3053
            0054 018B 1ED1 1ED0 2F03
            0058 0BC1 2F8A 0BC0 2F56
            005C 0063 305C 11C0 305C
            0060 11C1 305C 1CD0 2F03
            0064 0BC1 2F8A 0BC0 2F56
            0068 0063 3068 11C0 3068
            006C 11C1 3068 3056 3FFF


   1669266: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07EC 3FFF 0281 027A 1FFE
            07F0 0004 0004 3FFF 3FFF
            07F8 1850 3F54 3FFF 3FFF
            07FC 3FFF 3FFF 02FF 31FD


   1746862: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 3FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 3FFF 1
            07EB 1FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0004 0
            07F1 0004 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 02FF 1
            07FF 31FD 1

   1801641: FLASH_READ_A

            ADDR DATA ?
            -----------
            0000 0070 0
            0001 2F00 0
            0002 0182 0
            0003 3FED 0
            0004 018B 0
            0005 3FEE 1
            0006 019A 0
            0007 2F80 1
            0008 019B 0
            0009 2F1C 0
            000A 0183 0
            000B 1FFE 0
            000C 2AFF 0
            000D 1054 1
            000E 3FED 0
            000F 0B81 1
            0010 1F91 1
            0011 0F05 0
            0012 0B80 1
            0013 1AD0 0
            0014 3013 0
            0015 1F90 1
            0016 0063 1
            0017 3016 1
            0018 1180 0
            0019 1016 1
            001A 1D90 1
            001B 18D0 1
            001C 101B 1
            001D 2F01 1
            001E 1950 1
            001F 2FFF 0
            0020 0C01 1
            0021 018B 0
            0022 0B81 0
            0023 1AD0 0
            0024 1023 0
            0025 1B50 1
            0026 304F 1
            0027 2F04 1
            0028 0188 1
            0029 18D0 0
            002A 1029 0
            002B 2F02 1
            002C 0182 1
            002D 1304 0
            002E 1305 0
            002F 2F6E 1
            0030 0B82 1
            0031 2F00 0
            0032 0B83 0
            0033 0006 0
            0034 0B04 0
            0035 0007 0
            0036 0805 0
            0037 1584 0
            0038 1685 0
            0039 1004 1
            003A 1282 1
            003B 1083 1
            003C 1A40 1
            003D 3033 1
            003E 1F90 1
            003F 1AD0 1
            0040 303F 1
            0041 1584 1
            0042 1685 1
            0043 0590 1
            0044 18D0 1
            0045 1044 0
            0046 1950 1
            0047 103F 1
            0048 1D90 1
            0049 1AD0 1
            004A 1049 1
            004B 18D0 1
            004C 304B 1
            004D 1B50 1
            004E 102B 1
            004F 18D0 1
            0050 304F 1
            0051 1B50 1
            0052 1011 1
            0053 1053 1
            0054 018B 1
            0055 1ED1 1
            0056 1ED0 0
            0057 2F03 1
            0058 0BC1 1
            0059 2F8A 0
            005A 0BC0 0
            005B 2F56 0
            005C 0063 0
            005D 305C 0
            005E 11C0 0
            005F 305C 1
            0060 11C1 1
            0061 305C 1
            0062 1CD0 1
            0063 2F03 1
            0064 0BC1 1
            0065 2F8A 0
            0066 0BC0 0
            0067 2F56 0
            0068 0063 0
            0069 3068 0
            006A 11C0 0
            006B 3068 1
            006C 11C1 1
            006D 3068 1
            006E 3056 1
            006F 3FFF 1

   1890615: FLASH_READ_A
            No data (dummy read)

   1935310: FLASH_READ_B
            No data (dummy read)

   2004366: FLASH_WRITE_A

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            0000 0070 2F00 0182 3FED
            0004 018B 3FEE 019A 2F80
            0008 019B 2F1C 0183 3FFE
            000C 2AFF 3054 3FED 0B81
            0010 1F91 2F05 0B80 1AD0
            0014 3013 1F90 0063 3016
            0018 1180 3016 1D90 18D0
            001C 301B 2F01 1950 2FFF
            0020 0C01 018B 0B81 1AD0
            0024 3023 1B50 304F 2F04
            0028 0188 18D0 3029 2F02
            002C 0182 1304 1305 2F6E
            0030 0B82 2F00 0B83 0006
            0034 0B04 0007 0805 1584
            0038 1685 1004 1282 1083
            003C 1A40 3033 1F90 1AD0
            0040 303F 1584 1685 0590
            0044 18D0 3044 1950 303F
            0048 1D90 1AD0 3049 18D0
            004C 304B 1B50 302B 18D0
            0050 304F 1B50 3011 3053
            0054 018B 1ED1 1ED0 2F03
            0058 0BC1 2F8A 0BC0 2F56
            005C 0063 305C 11C0 305C
            0060 11C1 305C 1CD0 2F03
            0064 0BC1 2F8A 0BC0 2F56
            0068 0063 3068 11C0 3068
            006C 11C1 3068 3056 3FFF


   2110976: 0000001101001010001110011010010100011100
   2333060: 0000001101001010001110011010010100011100
   2584511: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07EC 3FFF 0281 027A 1FFE
            07F0 0004 0004 3FFF 3FFF
            07F8 1850 3F54 3FFF 3FFF
            07FC 3FFF 3FFF 0282 31FD


   2634228: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 1FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0004 0
            07F1 0004 1
            07F2 3FFF 0
            07F3 1FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

   2699086: FLASH_READ_B
            No data (dummy read)

   2743782: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07EC 3FFF 0281 027A 1FFE
            07F0 0004 0004 3FFF 3FFF
            07F8 1850 3F54 3FFF 3FFF
            07FC 3FFF 3FFF 0282 31FD


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 07:07:58 pm
There seems to be two Flash read commands and two Flash write commands - why? I have absolutely no idea.

    1010010110100101101001011010011100011010101000010: FLASH write A
    1010010110100101101001011010011100001010101000010: FLASH write B
    1010010110100101101001011010011000011010101000010: FLASH read A
    1010010110100101101001011010011000001010101000010: FLASH read B

This are the same commands I mentioned several posts ago.

    101001011010010110100101101001110001101010100001 (0): A5A5A5A *71* AA1   
    101001011010010110100101101001110000101010100001 (0): A5A5A5A *70* AA1
    101001011010010110100101101001100001101010100001 (0): A5A5A5A *61* AA1
    101001011010010110100101101001100000101010100001 (0): A5A5A5A *60* AA1

last bit (0) is clock when switching bus direction or delay before write?

==> https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2052700/#msg2052700 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2052700/#msg2052700)

I also wrote about the ERASE command 31 and maybe a CHECK command 66  (your 2 unknown commands).


The new captures contain the analog voltages of VDD and VPP. I wonder if different voltages are applied when the same commands are executed...?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 07:39:35 pm
First there is:
Code: [Select]
     55103: FLASH_READ_A

            ADDR DATA ?
            -----------
            07EF 1FFE 0
            07F0 0003 0
            07F1 0003 1

After that, the two mysterious commands are sent.
Code: [Select]
     92201: 1010010110100101101001011010001100011010101000010 0000
    158597: 1010010110100101101001011010011001111010101000010

Then, it does two writes:
Code: [Select]
    737022: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0004 3FFF 3FFF 3FFF

    820818: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 3FFF 0004 3FFF 3FFF

It finally does one read to verify it. As we can see, the two writes have been AND'ed, so it means FLASH_WRITE_B doesn't implicitely clear the FLASH and it had to be one of the mysterious that had been run before:
Code: [Select]
    949230: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0004 0
            07F1 0004 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1FFF 1
            07F9 3FFF 1
            07FA 1FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 1FFF 1
            07FF 3FFF 1

Either 0x60 or 0x31 have erased thus the last page (at least) of the memory, but I still don't see which would. Sending 0000 to erase last/all pages don't make much sense - I doubt there's only one page of flash and 0 means thus all.

0x60 being "clear everything" would make more sense (and thus would explain the long delay after executing that command while the device is being cleared), but I don't understand what 0x31 would do then.

EDIT: Also have a look at 0x7ED, still contains data after issuing those commands.

EDIT2: I don't know how to use the ZEROPLUS tool, so I don't really know how to see the VPP voltages.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 08:31:18 pm
EDIT2: I don't know how to use the ZEROPLUS tool, so I don't really know how to see the VPP voltages.

I grouped the 2 channels into a bus each (VDD_AN and PA5_ICVPP_AN, bottom of Zero Plus) which decodes to decimal values (right click on the hex values and select "Numeric Base->Decimal").

In case you want to do it manually:
C0...C7 = 8 bit of analog value VDD_AN (in 100mV, ==> 30 decimal = 3.0V, 45 decimal = 4.5V, ...)
D0...D7 = 8 bit of analog value PA5_ICVPP_AN


example line from text export:


         PA0_UNUSED   | Bus1           *VDD*SCLK*DATA PA4  PA5 PA7  GND   | VDD_AN              *C0...*C7  | PA5_ICVPP_AN  *D0...*D7   

91330            0    | Data=0X1F             1   0   0   0   1   0   0   | 0X2B                  11010100 | 0X38           00011100


VDD_AN = 11010100 = 0x2B = 43 ==> 4.3V
PA5_ICVPP_AN = 00011100 = 0x38 = 56 ==> 5.6V

 :)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 08:40:30 pm
Then, it does two writes:
Code: [Select]
    737022: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0004 3FFF 3FFF 3FFF

    820818: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 3FFF 0004 3FFF 3FFF

This looks pretty normal. To understand this you must know how a OTP / flash write is usually working.

Blank IC / After Erase => all memory cells are holding a '1' bit value
Programing = change some of the '1' bits to '0' bits. You only can change '1' to '0' not the other way around. If you want to write something new you must erase the chip first (is possible) which makes *ALL* memory cells to a '1'.

So
- writing '11111111' somewhere does in reality: NOTHING (all stays same, you can do this as many times as you want)
- writing '0' somewhere changes this bit to '0'. If you later write a '1' it will do NOTHING (the 0 will stay).


==> Since the IC seems to require to write 4 WORDS at once a simple solution just to write 1 WORD or even only some bits from it is to write the unused WORDS with all '1'.
- writing "ABCD 3FFF 3FFF 3FFF" only will change the first word
- writing "3FFF EFGH 3FFF 3FFF" only will change the second word

==> It looks like WRITER just wants to write 2 WORDS in 2 single operations.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 09:52:30 pm
Then, it does two writes:
Code: [Select]
    737022: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0004 3FFF 3FFF 3FFF

    820818: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 3FFF 0004 3FFF 3FFF

This looks pretty normal. To understand this you must know how a OTP / flash write is usually working.

Blank IC / After Erase => all memory cells are holding a '1' bit value
Programing = change some of the '1' bits to '0' bits. You only can change '1' to '0' not the other way around. If you want to write something new you must erase the chip first (is possible) which makes *ALL* memory cells to a '1'.

So
- writing '11111111' somewhere does in reality: NOTHING (all stays same, you can do this as many times as you want)
- writing '0' somewhere changes this bit to '0'. If you later write a '1' it will do NOTHING (the 0 will stay).


==> Since the IC seems to require to write 4 WORDS at once a simple solution just to write 1 WORD or even only some bits from it is to write the unused WORDS with all '1'.
- writing "ABCD 3FFF 3FFF 3FFF" only will change the first word
- writing "3FFF EFGH 3FFF 3FFF" only will change the second word

==> It looks like WRITER just wants to write 2 WORDS in 2 single operations.

JS
My point was that before the mysterious commands, 07F0 held 0003 and 07F1 held 0003. After them, they seem to held FFFF, which are subsequently changed into 0004 by those two writes.

However, you can see on 949230: FLASH_READ_B, that 07ED holds 0281. This means that "66" followed by four 0 bits, or "31" doesn't actually wipe all the flash, but if it actually actually wipes anything, it only clears a few bytes.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 10:37:24 pm
EDIT2: I don't know how to use the ZEROPLUS tool, so I don't really know how to see the VPP voltages.

I grouped the 2 channels into a bus each (VDD_AN and PA5_ICVPP_AN, bottom of Zero Plus) which decodes to decimal values (right click on the hex values and select "Numeric Base->Decimal").

In case you want to do it manually:
C0...C7 = 8 bit of analog value VDD_AN (in 100mV, ==> 30 decimal = 3.0V, 45 decimal = 4.5V, ...)
D0...D7 = 8 bit of analog value PA5_ICVPP_AN


example line from text export:


         PA0_UNUSED   | Bus1           *VDD*SCLK*DATA PA4  PA5 PA7  GND   | VDD_AN              *C0...*C7  | PA5_ICVPP_AN  *D0...*D7   

91330            0    | Data=0X1F             1   0   0   0   1   0   0   | 0X2B                  11010100 | 0X38           00011100


VDD_AN = 11010100 = 0x2B = 43 ==> 4.3V
PA5_ICVPP_AN = 00011100 = 0x38 = 56 ==> 5.6V

 :)

JS

Thanks. It seems that all commands are sent to the microcontroller with VDD 2.6V and VPP 5.6V.

After sending the command with those voltages:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 10:45:15 pm
My point was that before the mysterious commands, 07F0 held 0003 and 07F1 held 0003. After them, they seem to held FFFF, which are subsequently changed into 0004 by those two writes.

However, you can see on 949230: FLASH_READ_B, that 07ED holds 0281. This means that "66" followed by four 0 bits, or "31" doesn't actually wipe all the flash, but if it actually actually wipes anything, it only clears a few bytes.

Ok, got it now.

I think I know what it is... In WRITER I found a string telling the user that the flash chip is "overused" (when erased >1000 times).

So best guess is that they write the use count there. To be sure the value is always written correctly (not failed when power is lost during writing) they do it in 2 writes updating the 2 value.

 :)

Using "PADAUK-P-003-PFS154_SimpleBlink_NoPinCheck.txt" as example:

   55103: FLASH_READ_A

            ADDR DATA ?
            -----------
            07EF 1FFE 0
            07F0 0003 0
            07F1 0003 1

==> use count = 3

92201: ??? (1010010110100101101001011010001100011010101000010)
158597: ??? (1010010110100101101001011010011001111010101000010)
one of those is ERASE

    737022: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 0004 3FFF 3FFF 3FFF

    820818: FLASH_WRITE_B

            ADDR -W1- -W2- -W3- -W4-
            ------------------------
            07F0 3FFF 0004 3FFF 3FFF

949230: FLASH_READ_B

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 1FFF 0
            07E2 1FFF 1
            07E3 1FFF 1
            07E4 3FFF 1
            07E5 1FFF 1
            07E6 1FFF 1
            07E7 1FFF 1
            07E8 3FFF 1
            07E9 1FFF 1
            07EA 1FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0004 0
            07F1 0004 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1FFF 1
            07F9 3FFF 1
            07FA 1FFF 1
            07FB 3FFF 1
            07FC 1FFF 1
            07FD 3FFF 1
            07FE 1FFF 1
            07FF 3FFF 1

==> now use count is 4

BTW: This 0x1FFF read backs are for sure not correct. I know for sure that 0x3FFF is at most places there (in a previous posting I used LDSPTL/LDSPTH and soft SPI to read back the content of a real IC).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 10:56:36 pm
Hi,

  92201: ? ? ? (1010010110100101101001011010 00110001 1010101000010) => 0x31
158597: ? ? ? (1010010110100101101001011010 01100111 1010101000010) => 0x67

I still think command 31 is ERASE. Then WRITER waits internally some time doing nothing (assuming erase takes time) and then WRITER sends 0x67 (GET_STATUS or WAIT_FOR_ERASE_FINISH or ...) to find out if the erase finished for sure.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 25, 2018, 11:14:06 pm
My point was that before the mysterious commands, 07F0 held 0003 and 07F1 held 0003. After them, they seem to held FFFF, which are subsequently changed into 0004 by those two writes.
However, you can see on 949230: FLASH_READ_B, that 07ED holds 0281. This means that "66" followed by four 0 bits, or "31" doesn't actually wipe all the flash, but if it actually actually wipes anything, it only clears a few bytes.

I think those values (0x7ED, 0x7EE) might be FIXED for IC identification??. So they just can not get erased.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 25, 2018, 11:59:15 pm
BTW: This 0x1FFF read backs are for sure not correct. I know for sure that 0x3FFF is at most places there (in a previous posting I used LDSPTL/LDSPTH and soft SPI to read back the content of a real IC).
I am not sure, but it could be possible that data from writer to IC is sampled on the rising edge, but on the falling edge for the IC? maybe that's why I'm getting those weird, useless trailing bits and why they are sometimes read as 1FFF instead of 3FFF.
I think those values (0x7ED, 0x7EE) might be FIXED for IC identification??. So they just can not get erased.
That actually makes sense.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 26, 2018, 01:40:49 am
So apparently yes, the data from writer to IC gets sampled on rising edge, but from IC to writer gets sampled on the falling edge.

If we parse "Verify" on the falling edge we get:
Code: [Select]
    804582: FLASH_READ_A_N2

            ADDR DATA ?
            -----------
            0000 0060 0
            0001 1F00 0
            0002 0300 0
            0003 3FFA 0
            0004 0306 0
            0005 3FFC 1
            0006 0330 0
            0007 1F80 1
            0008 03B2 0
            0009 0E38 0
            000A 0302 0
            000B 3FFC 0
            000C 07FF 0
            000D 20E0 1
            000E 3FD8 0
            000F 1783 1
            0010 1F23 1
            0011 1E0B 0
            0012 1781 1
            0013 3C80 0
            0014 2023 0
            0015 1F01 1
            0016 00C3 1
            0017 300C 1
            0018 0180 0
            0019 2037 1
            001A 1F90 1
            001B 11D0 1
            001C 301B 1
            001D 2E03 1
            001E 19C0 1
            001F 2FFE 0
            0020 0C03 1
            0021 038F 0
            0022 0381 0
            0023 13F0 0
            0024 3022 0
            0025 3FC0 1
            0026 300F 1
            0027 2F0D 1
            0028 0118 1
            0029 3890 0
            002A 303B 0
            002B 2E00 1
            002C 0386 1
            002D 360C 0
            002E 230C 0
            002F 1EDF 1
            0030 1785 1
            0031 1F00 0
            0032 1F06 0
            0033 000C 0
            0034 1708 0
            0035 000E 0
            0036 100A 0
            0037 2B08 0
            0038 2D0A 0
            0039 2000 1
            003A 2405 1
            003B 2103 1
            003C 3481 1
            003D 2027 1
            003E 3F21 1
            003F 3DA1 1
            0040 207F 1
            0041 3B0D 1
            0042 250B 1
            0043 0B21 1
            0044 38A1 1
            0045 2008 0
            0046 3231 1
            0047 203F 1
            0048 3921 1
            0049 3C81 1
            004A 2001 1
            004B 31E1 1
            004C 2007 1
            004D 3F81 1
            004E 2047 1
            004F 3881 1
            0050 201F 1
            0051 3F81 1
            0052 2023 1
            0053 20B7 1
            0054 0197 1
            0055 1FE3 1
            0056 1EC0 0
            0057 3E03 1
            0058 0F83 1
            0059 2F82 0
            005A 03C0 0
            005B 2E16 0
            005C 0063 0
            005D 301C 0
            005E 03C0 0
            005F 30D8 1
            0060 11C3 1
            0061 30D8 1
            0062 3C90 1
            0063 2F03 1
            0064 1BC3 1
            0065 2F8E 0
            0066 0FC0 0
            0067 2E76 0
            0068 0062 0
            0069 3078 0
            006A 2380 0
            006B 30F8 1
            006C 2381 1
            006D 30F9 1
            006E 303F 1
            006F 3FFF 1
            0070 3FFF 1
            0071 3FFF 1
            0072 3FFF 1
            0073 3FFF 1
            0074 3FFF 1
            0075 3FFF 1
            0076 3FFF 1
            0077 3FFF 1
            0078 3FFF 1
            0079 3FFF 1
            007A 3FFF 1
            007B 3FFF 1
            007C 3FFF 1
            007D 3FFF 1
            007E 3FFF 1
            007F 3FFF 1
            0080 3FFF 1
            0081 3FFF 1
            0082 3FFF 1
            0083 3FFF 1
            0084 3FFF 1
            0085 3FFF 1
            0086 3FFF 1
            0087 3FFF 1
            0088 3FFF 1
            0089 3FFF 1
            008A 3FFF 1
            008B 3FFF 1
            008C 3FFF 1
            008D 3FFF 1
            008E 3FFF 1
            008F 3FFF 1
            0090 3FFF 1
            0091 3FFF 1
            0092 3FFF 1
            0093 3FFF 1
            0094 3FFF 1
            0095 3FFF 1
            0096 3FFF 1
            0097 3FFF 1
            0098 3FFF 1
            0099 3FFF 1
            009A 3FFF 1
            009B 3FFF 1
            009C 3FFF 1
            009D 3FFF 1
            009E 3FFF 1
            009F 3FFF 1
            00A0 3FFF 1
            00A1 3FFF 1
            00A2 3FFF 1
            00A3 3FFF 1
            00A4 3FFF 1
            00A5 3FFF 1
            00A6 3FFF 1
            00A7 3FFF 1
            00A8 3FFF 1
            00A9 3FFF 1
            00AA 3FFF 1
            00AB 3FFF 1
            00AC 3FFF 1
            00AD 3FFF 1
            00AE 3FFF 1
            00AF 3FFF 1
            00B0 3FFF 1
            00B1 3FFF 1
            00B2 3FFF 1
            00B3 3FFF 1
            00B4 3FFF 1
            00B5 3FFF 1
            00B6 3FFF 1
            00B7 3FFF 1
            00B8 3FFF 1
            00B9 3FFF 1
            00BA 3FFF 1
            00BB 3FFF 1
            00BC 3FFF 1
            00BD 3FFF 1
            00BE 3FFF 1
            00BF 3FFF 1
            00C0 3FFF 1
            00C1 3FFF 1
            00C2 3FFF 1
            00C3 3FFF 1
            00C4 3FFF 1
            00C5 3FFF 1
            00C6 3FFF 1
            00C7 3FFF 1
            00C8 3FFF 1
            00C9 3FFF 1
            00CA 3FFF 1
            00CB 3FFF 1
            00CC 3FFF 1
            00CD 3FFF 1
            00CE 3FFF 1
            00CF 3FFF 1
            00D0 3FFF 1
            00D1 3FFF 1
            00D2 3FFF 1
            00D3 3FFF 1
            00D4 3FFF 1
            00D5 3FFF 1
            00D6 3FFF 1
            00D7 3FFF 1
            00D8 3FFF 1
            00D9 3FFF 1
            00DA 3FFF 1
            00DB 3FFF 1
            00DC 3FFF 1
            00DD 3FFF 1
            00DE 3FFF 1
            00DF 3FFF 1
            00E0 3FFF 1
            00E1 3FFF 1
            00E2 3FFF 1
            00E3 3FFF 1
            00E4 3FFF 1
            00E5 3FFF 1
            00E6 3FFF 1
            00E7 3FFF 1
            00E8 3FFF 1
            00E9 3FFF 1
            00EA 3FFF 1
            00EB 3FFF 1
            00EC 3FFF 1
            00ED 3FFF 1
            00EE 3FFF 1
            00EF 3FFF 1
            00F0 3FFF 1
            00F1 3FFF 1
            00F2 3FFF 1
            00F3 3FFF 1
            00F4 3FFF 1
            00F5 3FFF 1
            00F6 3FFF 1
            00F7 3FFF 1
            00F8 3FFF 1
            00F9 3FFF 1
            00FA 3FFF 1
            00FB 3FFF 1
            00FC 3FFF 1
            00FD 3FFF 1
            00FE 3FFF 1
            00FF 3FFF 1
            0100 3FFF 1
            0101 3FFF 1
            0102 3FFF 1
            0103 3FFF 1
            0104 3FFF 1
            0105 3FFF 1
            0106 3FFF 1
            0107 3FFF 1
            0108 3FFF 1
            0109 3FFF 1
            010A 3FFF 1
            010B 3FFF 1
            010C 3FFF 1
            010D 3FFF 1
            010E 3FFF 1
            010F 3FFF 1
            0110 3FFF 1
            0111 3FFF 1
            0112 3FFF 1
            0113 3FFF 1
            0114 3FFF 1
            0115 3FFF 1
            0116 3FFF 1
            0117 3FFF 1
            0118 3FFF 1
            0119 3FFF 1
            011A 3FFF 1
            011B 3FFF 1
            011C 3FFF 1
            011D 3FFF 1
            011E 3FFF 1
            011F 3FFF 1
            0120 3FFF 1
            0121 3FFF 1
            0122 3FFF 1
            0123 3FFF 1
            0124 3FFF 1
            0125 3FFF 1
            0126 3FFF 1
            0127 3FFF 1
            0128 3FFF 1
            0129 3FFF 1
            012A 3FFF 1
            012B 3FFF 1
            012C 3FFF 1
            012D 3FFF 1
            012E 3FFF 1
            012F 3FFF 1
            0130 3FFF 1
            0131 3FFF 1
            0132 3FFF 1
            0133 3FFF 1
            0134 3FFF 1
            0135 3FFF 1
            0136 3FFF 1
            0137 3FFF 1
            0138 3FFF 1
            0139 3FFF 1
            013A 3FFF 1
            013B 3FFF 1
            013C 3FFF 1
            013D 3FFF 1
            013E 3FFF 1
            013F 3FFF 1
            0140 3FFF 1
            0141 3FFF 1
            0142 3FFF 1
            0143 3FFF 1
            0144 3FFF 1
            0145 3FFF 1
            0146 3FFF 1
            0147 3FFF 1
            0148 3FFF 1
            0149 3FFF 1
            014A 3FFF 1
            014B 3FFF 1
            014C 3FFF 1
            014D 3FFF 1
            014E 3FFF 1
            014F 3FFF 1
            0150 3FFF 1
            0151 3FFF 1
            0152 3FFF 1
            0153 3FFF 1
            0154 3FFF 1
            0155 3FFF 1
            0156 3FFF 1
            0157 3FFF 1
            0158 3FFF 1
            0159 3FFF 1
            015A 3FFF 1
            015B 3FFF 1
            015C 3FFF 1
            015D 3FFF 1
            015E 3FFF 1
            015F 3FFF 1
            0160 3FFF 1
            0161 3FFF 1
            0162 3FFF 1
            0163 3FFF 1
            0164 3FFF 1
            0165 3FFF 1
            0166 3FFF 1
            0167 3FFF 1
            0168 3FFF 1
            0169 3FFF 1
            016A 3FFF 1
            016B 3FFF 1
            016C 3FFF 1
            016D 3FFF 1
            016E 3FFF 1
            016F 3FFF 1
            0170 3FFF 1
            0171 3FFF 1
            0172 3FFF 1
            0173 3FFF 1
            0174 3FFF 1
            0175 3FFF 1
            0176 3FFF 1
            0177 3FFF 1
            0178 3FFF 1
            0179 3FFF 1
            017A 3FFF 1
            017B 3FFF 1
            017C 3FFF 1
            017D 3FFF 1
            017E 3FFF 1
            017F 3FFF 1
            0180 3FFF 1
            0181 3FFF 1
            0182 3FFF 1
            0183 3FFF 1
            0184 3FFF 1
            0185 3FFF 1
            0186 3FFF 1
            0187 3FFF 1
            0188 3FFF 1
            0189 3FFF 1
            018A 3FFF 1
            018B 3FFF 1
            018C 3FFF 1
            018D 3FFF 1
            018E 3FFF 1
            018F 3FFF 1
            0190 3FFF 1
            0191 3FFF 1
            0192 3FFF 1
            0193 3FFF 1
            0194 3FFF 1
            0195 3FFF 1
            0196 3FFF 1
            0197 3FFF 1
            0198 3FFF 1
            0199 3FFF 1
            019A 3FFF 1
            019B 3FFF 1
            019C 3FFF 1
            019D 3FFF 1
            019E 3FFF 1
            019F 3FFF 1
            01A0 3FFF 1
            01A1 3FFF 1
            01A2 3FFF 1
            01A3 3FFF 1
            01A4 3FFF 1
            01A5 3FFF 1
            01A6 3FFF 1
            01A7 3FFF 1
            01A8 3FFF 1
            01A9 3FFF 1
            01AA 3FFF 1
            01AB 3FFF 1
            01AC 3FFF 1
            01AD 3FFF 1
            01AE 3FFF 1
            01AF 3FFF 1
            01B0 3FFF 1
            01B1 3FFF 1
            01B2 3FFF 1
            01B3 3FFF 1
            01B4 3FFF 1
            01B5 3FFF 1
            01B6 3FFF 1
            01B7 3FFF 1
            01B8 3FFF 1
            01B9 3FFF 1
            01BA 3FFF 1
            01BB 3FFF 1
            01BC 3FFF 1
            01BD 3FFF 1
            01BE 3FFF 1
            01BF 3FFF 1
            01C0 3FFF 1
            01C1 3FFF 1
            01C2 3FFF 1
            01C3 3FFF 1
            01C4 3FFF 1
            01C5 3FFF 1
            01C6 3FFF 1
            01C7 3FFF 1
            01C8 3FFF 1
            01C9 3FFF 1
            01CA 3FFF 1
            01CB 3FFF 1
            01CC 3FFF 1
            01CD 3FFF 1
            01CE 3FFF 1
            01CF 3FFF 1
            01D0 3FFF 1
            01D1 3FFF 1
            01D2 3FFF 1
            01D3 3FFF 1
            01D4 3FFF 1
            01D5 3FFF 1
            01D6 3FFF 1
            01D7 3FFF 1
            01D8 3FFF 1
            01D9 3FFF 1
            01DA 3FFF 1
            01DB 3FFF 1
            01DC 3FFF 1
            01DD 3FFF 1
            01DE 3FFF 1
            01DF 3FFF 1
            01E0 3FFF 1
            01E1 3FFF 1
            01E2 3FFF 1
            01E3 3FFF 1
            01E4 3FFF 1
            01E5 3FFF 1
            01E6 3FFF 1
            01E7 3FFF 1
            01E8 3FFF 1
            01E9 3FFF 1
            01EA 3FFF 1
            01EB 3FFF 1
            01EC 3FFF 1
            01ED 3FFF 1
            01EE 3FFF 1
            01EF 3FFF 1
            01F0 3FFF 1
            01F1 3FFF 1
            01F2 3FFF 1
            01F3 3FFF 1
            01F4 3FFF 1
            01F5 3FFF 1
            01F6 3FFF 1
            01F7 3FFF 1
            01F8 3FFF 1
            01F9 3FFF 1
            01FA 3FFF 1
            01FB 3FFF 1
            01FC 3FFF 1
            01FD 3FFF 1
            01FE 3FFF 1
            01FF 3FFF 1
            0200 3FFF 1
            0201 3FFF 1
            0202 3FFF 1
            0203 3FFF 1
            0204 3FFF 1
            0205 3FFF 1
            0206 3FFF 1
            0207 3FFF 1
            0208 3FFF 1
            0209 3FFF 1
            020A 3FFF 1
            020B 3FFF 1
            020C 3FFF 1
            020D 3FFF 1
            020E 3FFF 1
            020F 3FFF 1
            0210 3FFF 1
            0211 3FFF 1
            0212 3FFF 1
            0213 3FFF 1
            0214 3FFF 1
            0215 3FFF 1
            0216 3FFF 1
            0217 3FFF 1
            0218 3FFF 1
            0219 3FFF 1
            021A 3FFF 1
            021B 3FFF 1
            021C 3FFF 1
            021D 3FFF 1
            021E 3FFF 1
            021F 3FFF 1
            0220 3FFF 1
            0221 3FFF 1
            0222 3FFF 1
            0223 3FFF 1
            0224 3FFF 1
            0225 3FFF 1
            0226 3FFF 1
            0227 3FFF 1
            0228 3FFF 1
            0229 3FFF 1
            022A 3FFF 1
            022B 3FFF 1
            022C 3FFF 1
            022D 3FFF 1
            022E 3FFF 1
            022F 3FFF 1
            0230 3FFF 1
            0231 3FFF 1
            0232 3FFF 1
            0233 3FFF 1
            0234 3FFF 1
            0235 3FFF 1
            0236 3FFF 1
            0237 3FFF 1
            0238 3FFF 1
            0239 3FFF 1
            023A 3FFF 1
            023B 3FFF 1
            023C 3FFF 1
            023D 3FFF 1
            023E 3FFF 1
            023F 3FFF 1
            0240 3FFF 1
            0241 3FFF 1
            0242 3FFF 1
            0243 3FFF 1
            0244 3FFF 1
            0245 3FFF 1
            0246 3FFF 1
            0247 3FFF 1
            0248 3FFF 1
            0249 3FFF 1
            024A 3FFF 1
            024B 3FFF 1
            024C 3FFF 1
            024D 3FFF 1
            024E 3FFF 1
            024F 3FFF 1
            0250 3FFF 1
            0251 3FFF 1
            0252 3FFF 1
            0253 3FFF 1
            0254 3FFF 1
            0255 3FFF 1
            0256 3FFF 1
            0257 3FFF 1
            0258 3FFF 1
            0259 3FFF 1
            025A 3FFF 1
            025B 3FFF 1
            025C 3FFF 1
            025D 3FFF 1
            025E 3FFF 1
            025F 3FFF 1
            0260 3FFF 1
            0261 3FFF 1
            0262 3FFF 1
            0263 3FFF 1
            0264 3FFF 1
            0265 3FFF 1
            0266 3FFF 1
            0267 3FFF 1
            0268 3FFF 1
            0269 3FFF 1
            026A 3FFF 1
            026B 3FFF 1
            026C 3FFF 1
            026D 3FFF 1
            026E 3FFF 1
            026F 3FFF 1
            0270 3FFF 1
            0271 3FFF 1
            0272 3FFF 1
            0273 3FFF 1
            0274 3FFF 1
            0275 3FFF 1
            0276 3FFF 1
            0277 3FFF 1
            0278 3FFF 1
            0279 3FFF 1
            027A 3FFF 1
            027B 3FFF 1
            027C 3FFF 1
            027D 3FFF 1
            027E 3FFF 1
            027F 3FFF 1
            0280 3FFF 1
            0281 3FFF 1
            0282 3FFF 1
            0283 3FFF 1
            0284 3FFF 1
            0285 3FFF 1
            0286 3FFF 1
            0287 3FFF 1
            0288 3FFF 1
            0289 3FFF 1
            028A 3FFF 1
            028B 3FFF 1
            028C 3FFF 1
            028D 3FFF 1
            028E 3FFF 1
            028F 3FFF 1
            0290 3FFF 1
            0291 3FFF 1
            0292 3FFF 1
            0293 3FFF 1
            0294 3FFF 1
            0295 3FFF 1
            0296 3FFF 1
            0297 3FFF 1
            0298 3FFF 1
            0299 3FFF 1
            029A 3FFF 1
            029B 3FFF 1
            029C 3FFF 1
            029D 3FFF 1
            029E 3FFF 1
            029F 3FFF 1
            02A0 3FFF 1
            02A1 3FFF 1
            02A2 3FFF 1
            02A3 3FFF 1
            02A4 3FFF 1
            02A5 3FFF 1
            02A6 3FFF 1
            02A7 3FFF 1
            02A8 3FFF 1
            02A9 3FFF 1
            02AA 3FFF 1
            02AB 3FFF 1
            02AC 3FFF 1
            02AD 3FFF 1
            02AE 3FFF 1
            02AF 3FFF 1
            02B0 3FFF 1
            02B1 3FFF 1
            02B2 3FFF 1
            02B3 3FFF 1
            02B4 3FFF 1
            02B5 3FFF 1
            02B6 3FFF 1
            02B7 3FFF 1
            02B8 3FFF 1
            02B9 3FFF 1
            02BA 3FFF 1
            02BB 3FFF 1
            02BC 3FFF 1
            02BD 3FFF 1
            02BE 3FFF 1
            02BF 3FFF 1
            02C0 3FFF 1
            02C1 3FFF 1
            02C2 3FFF 1
            02C3 3FFF 1
            02C4 3FFF 1
            02C5 3FFF 1
            02C6 3FFF 1
            02C7 3FFF 1
            02C8 3FFF 1
            02C9 3FFF 1
            02CA 3FFF 1
            02CB 3FFF 1
            02CC 3FFF 1
            02CD 3FFF 1
            02CE 3FFF 1
            02CF 3FFF 1
            02D0 3FFF 1
            02D1 3FFF 1
            02D2 3FFF 1
            02D3 3FFF 1
            02D4 3FFF 1
            02D5 3FFF 1
            02D6 3FFF 1
            02D7 3FFF 1
            02D8 3FFF 1
            02D9 3FFF 1
            02DA 3FFF 1
            02DB 3FFF 1
            02DC 3FFF 1
            02DD 3FFF 1
            02DE 3FFF 1
            02DF 3FFF 1
            02E0 3FFF 1
            02E1 3FFF 1
            02E2 3FFF 1
            02E3 3FFF 1
            02E4 3FFF 1
            02E5 3FFF 1
            02E6 3FFF 1
            02E7 3FFF 1
            02E8 3FFF 1
            02E9 3FFF 1
            02EA 3FFF 1
            02EB 3FFF 1
            02EC 3FFF 1
            02ED 3FFF 1
            02EE 3FFF 1
            02EF 3FFF 1
            02F0 3FFF 1
            02F1 3FFF 1
            02F2 3FFF 1
            02F3 3FFF 1
            02F4 3FFF 1
            02F5 3FFF 1
            02F6 3FFF 1
            02F7 3FFF 1
            02F8 3FFF 1
            02F9 3FFF 1
            02FA 3FFF 1
            02FB 3FFF 1
            02FC 3FFF 1
            02FD 3FFF 1
            02FE 3FFF 1
            02FF 3FFF 1
            0300 3FFF 1
            0301 3FFF 1
            0302 3FFF 1
            0303 3FFF 1
            0304 3FFF 1
            0305 3FFF 1
            0306 3FFF 1
            0307 3FFF 1
            0308 3FFF 1
            0309 3FFF 1
            030A 3FFF 1
            030B 3FFF 1
            030C 3FFF 1
            030D 3FFF 1
            030E 3FFF 1
            030F 3FFF 1
            0310 3FFF 1
            0311 3FFF 1
            0312 3FFF 1
            0313 3FFF 1
            0314 3FFF 1
            0315 3FFF 1
            0316 3FFF 1
            0317 3FFF 1
            0318 3FFF 1
            0319 3FFF 1
            031A 3FFF 1
            031B 3FFF 1
            031C 3FFF 1
            031D 3FFF 1
            031E 3FFF 1
            031F 3FFF 1
            0320 3FFF 1
            0321 3FFF 1
            0322 3FFF 1
            0323 3FFF 1
            0324 3FFF 1
            0325 3FFF 1
            0326 3FFF 1
            0327 3FFF 1
            0328 3FFF 1
            0329 3FFF 1
            032A 3FFF 1
            032B 3FFF 1
            032C 3FFF 1
            032D 3FFF 1
            032E 3FFF 1
            032F 3FFF 1
            0330 3FFF 1
            0331 3FFF 1
            0332 3FFF 1
            0333 3FFF 1
            0334 3FFF 1
            0335 3FFF 1
            0336 3FFF 1


The unknown bit is thus probably just garbage from switching from input to output.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 26, 2018, 04:32:52 am
Some more info about the jumpers of the programmer. If you connect JP2, you will have the following pinout at the 40 pin ZIF socket:

pinsignal
5VDD
6PA7
7PA6
8PA5
33PA3
34PA4
35PA0
36GND

As described in my last posting, the bottom 8 pins of the ZIF socket are always connected to the programmer signals, and the jumpers are just connecting it to the other pins. This means you can measure the pinout for the other jumpers with a continuity tester.

For my Padauk SOT-23-6 to DIP14 adapter this means I just have to insert the adapter with a shift of 1, see attached image. Then I can use this writer line in my PRE file and it works:

Code: [Select]
.writer package 14, 4, 32, 8, 9, 7, 6, 32, 11, 0x0000, 0x0000, 1

The last number 1 is for the IC shift. But the connections are defined by the jumpers, so you can't just set it to any value you want. I guess it is only used for the open/short tests and for the GUI.

So no need anymore for a custom connector board or the jumper wire mess on JP7 :) Maybe this helps someone who also have a PMS150C in SOT-23-6, the manual is not very clear about the required writer setup. BTW, when starting the writer software, it still says "Check Jump: S08: JP2 /IC Shift 4". I guess it reads this from an internal database for the PMS150C chip, and ignores the custom writer declaration of the PDK file. It still works, just insert it with a IC shift of 1.

PS: how were the nice chip diagrams at https://free-pdk.github.io drawn? I used KiCad for my diagram and copied it to Gimp and then edited it there, but I guess there is some software out there which makes it easier?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 26, 2018, 09:48:53 am
So apparently yes, the data from writer to IC gets sampled on rising edge, but from IC to writer gets sampled on the falling edge.

If we parse "Verify" on the falling edge we get:
Code: [Select]
    804582: FLASH_READ_A_N2

            ADDR DATA ?
            -----------
            0000 0060 0
            0001 1F00 0
            0002 0300 0
...

The unknown bit is thus probably just garbage from switching from input to output.

Unfortunately this does not seem right as well. "Verify" should read back the same content as in SimpleBlink PDK starting with "0070 ...".

I made a new capture of "Verify" using higher sampling frequency (5MHz). Maybe this will solve the "read" instability.
To increase buffer size I removed the analog voltage capture.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 26, 2018, 10:20:16 am
PS: how were the nice chip diagrams at https://free-pdk.github.io drawn? I used KiCad for my diagram and copied it to Gimp and then edited it there, but I guess there is some software out there which makes it easier?

Hi,

I repurposed "James' Dodgy Arduino-Oriented Pinout Maker For Microcontrollers" from here: https://github.com/sleemanj/ArduinoOrientedChipPinoutCreator
Just some hacking and fiddeling later it is now possible to create one of those pictures using just a simple syntax like this:

Code: [Select]
        {
          Name   : 'PFS154-S16/D16',
          Package: '2SIDED'  ,
          Pins   :  16     ,
          PRC    :   { Vcc:5, Gnd:12, Reset: 8, XTAL1: 6, XTAL2:7 },
          PWM    :   [1,2,3,4,8,9,10,11,15,16],
          PA :   [11,0,0,9,10,8,7,6],
          PB :   [13,14,15,16,1,2,3,4],
          Analog :   [],
          Peripherals: { }
        }


One big problem is to capture the output image. Right now I print it to PDF or just take a screenshot from browser.
I plan to automate this by adding a canvas capture and save to image function later.

When all is fixed I will release the generator on github.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 26, 2018, 11:01:19 am
So apparently yes, the data from writer to IC gets sampled on rising edge, but from IC to writer gets sampled on the falling edge.

If we parse "Verify" on the falling edge we get:
Code: [Select]
    804582: FLASH_READ_A_N2

            ADDR DATA ?
            -----------
            0000 0060 0
            0001 1F00 0
            0002 0300 0
...


The unknown bit is thus probably just garbage from switching from input to output.

Unfortunately this does not seem right as well. "Verify" should read back the same content as in SimpleBlink PDK starting with "0070 ...".

I made a new capture of "Verify" using higher sampling frequency (5MHz). Maybe this will solve the "read" instability.
To increase buffer size I removed the analog voltage capture.

JS
Code: [Select]
      2527: FLASH_READ_A
            No data (dummy read)

     67967: FLASH_READ_A
            No data (dummy read)

    179611: FLASH_READ_A

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 3FFF 1
            07E6 3FFF 1
            07E7 3FFF 1
            07E8 3FFF 1
            07E9 3FFF 1
            07EA 3FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027A 1
            07EF 1FFE 0
            07F0 0027 0
            07F1 0025 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F74 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 3FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

    316754: FLASH_READ_A
            No data (dummy read)

   1711828: FLASH_READ_A

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 3FFF 1
            07E6 3FFF 1
            07E7 3FFF 1
            07E8 3FFF 1
            07E9 3FFF 1
            07EA 3FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0681 1
            07EE 027E 1
            07EF 1FFE 0
            07F0 0065 0
            07F1 0025 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F74 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 3FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

   1848671: FLASH_READ_A

            ADDR DATA ?
            -----------
            07E0 3FFF 0
            07E1 3FFF 0
            07E2 3FFF 1
            07E3 3FFF 1
            07E4 3FFF 1
            07E5 3FFF 1
            07E6 3FFF 1
            07E7 3FFF 1
            07E8 3FFF 1
            07E9 3FFF 1
            07EA 3FFF 1
            07EB 3FFF 1
            07EC 3FFF 1
            07ED 0281 1
            07EE 027E 1
            07EF 3FFE 0
            07F0 006D 0
            07F1 006D 1
            07F2 3FFF 0
            07F3 3FFF 0
            07F4 3FFF 1
            07F5 3FFF 1
            07F6 3FFF 1
            07F7 3FFF 1
            07F8 1850 1
            07F9 3F54 1
            07FA 3FFF 1
            07FB 3FFF 1
            07FC 3FFF 1
            07FD 3FFF 1
            07FE 0282 1
            07FF 31FD 1

   1985807: FLASH_READ_A

            ADDR DATA ?
            -----------
            0000 0070 0
            0001 2F00 0
            0002 0182 0
            0003 3FED 0
            0004 018B 0
            0005 3FEE 1
            0006 019E 0
            0007 2F81 1
            0008 019B 0
            0009 2F1C 0
            000A 0183 0
            000B 3FFE 0
            000C 2BFF 0
            000D 30D4 1
            000E 3FED 0
            000F 0B81 1
            0010 1F91 1
            0011 2F05 0
            0012 0B80 1
            0013 1AD0 0
            0014 3013 0
            0015 1F90 1
            0016 0063 1
            0017 3016 1
            0018 1180 0
            0019 3016 1
            001A 3D90 1
            001B 18D0 1
            001C 301B 1
            001D 2F01 1
            001E 1950 1
            001F 2FFF 0
            0020 1C01 1
            0021 018B 0
            0022 0B83 0
            0023 3AD0 0
            0024 3023 0
            0025 1B50 1
            0026 304F 1
            0027 2F04 1
            0028 0188 1
            0029 18D0 0
            002A 3029 0
            002B 2F02 1
            002C 0182 1
            002D 1304 0
            002E 1305 0
            002F 2F6E 1
            0030 0B82 1
            0031 2F00 0
            0032 0B83 0
            0033 0006 0
            0034 0B04 0
            0035 0007 0
            0036 0805 0
            0037 1584 0
            0038 1685 0
            0039 1004 1
            003A 1282 1
            003B 3083 1
            003C 1A40 1
            003D 3077 1
            003E 1FB0 1
            003F 1ED1 1
            0040 303F 1
            0041 1D84 1
            0042 1685 1
            0043 0591 1
            0044 18D0 1
            0045 3044 0
            0046 1950 1
            0047 303F 1
            0048 1D90 1
            0049 1BF0 1
            004A 3049 1
            004B 18D0 1
            004C 304B 1
            004D 1B50 1
            004E 302B 1
            004F 18D0 1
            0050 304F 1
            0051 1B50 1
            0052 3011 1
            0053 3053 1
            0054 018B 1
            0055 1ED1 1
            0056 1ED0 0
            0057 2F07 1
            0058 0BC1 1
            0059 2F8A 0
            005A 1BC0 0
            005B 2FD6 0
            005C 0063 0
            005D 30DC 0
            005E 11C0 0
            005F 305C 1
            0060 11C1 1
            0061 305C 1
            0062 1CD0 1
            0063 2F03 1
            0064 0BC1 1
            0065 2F8E 0
            0066 0BC0 0
            0067 2F56 0
            0068 0063 0
            0069 3068 0
            006A 11C0 0
            006B 3068 1
            006C 31C1 1
            006D 3068 1
            006E 3056 1
            006F 3FFF 1
            0070 3FFF 1
            0071 3FFF 1
            0072 3FFF 1
            0073 3FFF 1
            0074 3FFF 1
            0075 3FFF 1
            0076 3FFF 1
            0077 3FFF 1
            0078 3FFF 1
            0079 3FFF 1
            007A 3FFF 1
            007B 3FFF 1
            007C 3FFF 1
            007D 3FFF 1
            007E 3FFF 1
            007F 3FFF 1
            0080 3FFF 1
            0081 3FFF 1
            0082 3FFF 1
            0083 3FFF 1
            0084 3FFF 1
            0085 3FFF 1
            0086 3FFF 1
            0087 3FFF 1
            0088 3FFF 1
            0089 3FFF 1
            008A 3FFF 1
            008B 3FFF 1
            008C 3FFF 1
            008D 3FFF 1
            008E 3FFF 1
            008F 3FFF 1
            0090 3FFF 1
            0091 3FFF 1
            0092 3FFF 1
            0093 3FFF 1
            0094 3FFF 1
            0095 3FFF 1
            0096 3FFF 1
            0097 3FFF 1
            0098 3FFF 1
            0099 3FFF 1
            009A 3FFF 1
            009B 3FFF 1
            009C 3FFF 1
            009D 3FFF 1
            009E 3FFF 1
            009F 3FFF 1
            00A0 3FFF 1
            00A1 3FFF 1
            00A2 3FFF 1
            00A3 3FFF 1
            00A4 3FFF 1
            00A5 3FFF 1
            00A6 3FFF 1
            00A7 3FFF 1
            00A8 3FFF 1
            00A9 3FFF 1
            00AA 3FFF 1
            00AB 3FFF 1
            00AC 3FFF 1
            00AD 3FFF 1
            00AE 3FFF 1
            00AF 3FFF 1
            00B0 3FFF 1
            00B1 3FFF 1
            00B2 3FFF 1
            00B3 3FFF 1
            00B4 3FFF 1
            00B5 3FFF 1
            00B6 3FFF 1
            00B7 3FFF 1
            00B8 3FFF 1
            00B9 3FFF 1
            00BA 3FFF 1
            00BB 3FFF 1
            00BC 3FFF 1
            00BD 3FFF 1
            00BE 3FFF 1
            00BF 3FFF 1
            00C0 3FFF 1
            00C1 3FFF 1
            00C2 3FFF 1
            00C3 3FFF 1
            00C4 3FFF 1
            00C5 3FFF 1
            00C6 3FFF 1
            00C7 3FFF 1
            00C8 3FFF 1
            00C9 3FFF 1
            00CA 3FFF 1
            00CB 3FFF 1
            00CC 3FFF 1
            00CD 3FFF 1
            00CE 3FFF 1
            00CF 3FFF 1
            00D0 3FFF 1
            00D1 3FFF 1
            00D2 3FFF 1
            00D3 3FFF 1
            00D4 3FFF 1
            00D5 3FFF 1
            00D6 3FFF 1
            00D7 3FFF 1
            00D8 3FFF 1
            00D9 3FFF 1
            00DA 3FFF 1
            00DB 3FFF 1
            00DC 3FFF 1
            00DD 3FFF 1
            00DE 3FFF 1
            00DF 3FFF 1
            00E0 3FFF 1
            00E1 3FFF 1
            00E2 3FFF 1
            00E3 3FFF 1
            00E4 3FFF 1
            00E5 3FFF 1
            00E6 3FFF 1
            00E7 3FFF 1
            00E8 3FFF 1
            00E9 3FFF 1
            00EA 3FFF 1
            00EB 3FFF 1
            00EC 3FFF 1
            00ED 3FFF 1
            00EE 3FFF 1
            00EF 3FFF 1
            00F0 3FFF 1
            00F1 3FFF 1
            00F2 3FFF 1
            00F3 3FFF 1
            00F4 3FFF 1
            00F5 3FFF 1
            00F6 3FFF 1
            00F7 3FFF 1
            00F8 3FFF 1
            00F9 3FFF 1
            00FA 3FFF 1
            00FB 3FFF 1
            00FC 3FFF 1
            00FD 3FFF 1
            00FE 3FFF 1
            00FF 3FFF 1
            0100 3FFF 1
            0101 3FFF 1
            0102 3FFF 1
            0103 3FFF 1
            0104 3FFF 1
            0105 3FFF 1
            0106 3FFF 1
            0107 3FFF 1
            0108 3FFF 1
            0109 3FFF 1
            010A 3FFF 1
            010B 3FFF 1
            010C 3FFF 1
            010D 3FFF 1
            010E 3FFF 1
            010F 3FFF 1
            0110 3FFF 1
            0111 3FFF 1
            0112 3FFF 1
            0113 3FFF 1
            0114 3FFF 1
            0115 3FFF 1
            0116 3FFF 1
            0117 3FFF 1
            0118 3FFF 1
            0119 3FFF 1
            011A 3FFF 1
            011B 3FFF 1
            011C 3FFF 1
            011D 3FFF 1
            011E 3FFF 1
            011F 3FFF 1
            0120 3FFF 1
            0121 3FFF 1
            0122 3FFF 1
            0123 3FFF 1
            0124 3FFF 1
            0125 3FFF 1
            0126 3FFF 1
            0127 3FFF 1
            0128 3FFF 1
            0129 3FFF 1
            012A 3FFF 1
            012B 3FFF 1
            012C 3FFF 1
            012D 3FFF 1
            012E 3FFF 1
            012F 3FFF 1
            0130 3FFF 1
            0131 3FFF 1
            0132 3FFF 1
            0133 3FFF 1
            0134 3FFF 1
            0135 3FFF 1
            0136 3FFF 1
            0137 3FFF 1
            0138 3FFF 1
            0139 3FFF 1
            013A 3FFF 1
            013B 3FFF 1
            013C 3FFF 1
            013D 3FFF 1
            013E 3FFF 1
            013F 3FFF 1
            0140 3FFF 1
            0141 3FFF 1
            0142 3FFF 1
            0143 3FFF 1
            0144 3FFF 1
            0145 3FFF 1
            0146 3FFF 1
            0147 3FFF 1
            0148 3FFF 1
            0149 3FFF 1
            014A 3FFF 1
            014B 3FFF 1
            014C 3FFF 1
            014D 3FFF 1
            014E 3FFF 1
            014F 3FFF 1
            0150 3FFF 1
            0151 3FFF 1
            0152 3FFF 1
            0153 3FFF 1
            0154 3FFF 1
            0155 3FFF 1
            0156 3FFF 1
            0157 3FFF 1
            0158 3FFF 1
            0159 3FFF 1
            015A 3FFF 1
            015B 3FFF 1
            015C 3FFF 1
            015D 3FFF 1
            015E 3FFF 1
            015F 3FFF 1
            0160 3FFF 1
            0161 3FFF 1
            0162 3FFF 1
            0163 3FFF 1
            0164 3FFF 1
            0165 3FFF 1
            0166 3FFF 1
            0167 3FFF 1
            0168 3FFF 1
            0169 3FFF 1
            016A 3FFF 1
            016B 3FFF 1
            016C 3FFF 1
            016D 3FFF 1
            016E 3FFF 1
            016F 3FFF 1
            0170 3FFF 1
            0171 3FFF 1
            0172 3FFF 1
            0173 3FFF 1
            0174 3FFF 1
            0175 3FFF 1
            0176 3FFF 1
            0177 3FFF 1
            0178 3FFF 1
            0179 3FFF 1
            017A 3FFF 1
            017B 3FFF 1
            017C 3FFF 1
            017D 3FFF 1
            017E 3FFF 1
            017F 3FFF 1
            0180 3FFF 1
            0181 3FFF 1
            0182 3FFF 1
            0183 3FFF 1
            0184 3FFF 1
            0185 3FFF 1
            0186 3FFF 1
            0187 3FFF 1
            0188 3FFF 1
            0189 3FFF 1
            018A 3FFF 1
            018B 3FFF 1
            018C 3FFF 1
            018D 3FFF 1
            018E 3FFF 1
            018F 3FFF 1
            0190 3FFF 1
            0191 3FFF 1
            0192 3FFF 1
            0193 3FFF 1
            0194 3FFF 1
            0195 3FFF 1
            0196 3FFF 1
            0197 3FFF 1
            0198 3FFF 1
            0199 3FFF 1
            019A 3FFF 1
            019B 3FFF 1
            019C 3FFF 1
            019D 3FFF 1
            019E 3FFF 1
            019F 3FFF 1
            01A0 3FFF 1
            01A1 3FFF 1
            01A2 3FFF 1
            01A3 3FFF 1
            01A4 3FFF 1
            01A5 3FFF 1
            01A6 3FFF 1
            01A7 3FFF 1
            01A8 3FFF 1
            01A9 3FFF 1
            01AA 3FFF 1
            01AB 3FFF 1
            01AC 3FFF 1
            01AD 3FFF 1
            01AE 3FFF 1
            01AF 3FFF 1
            01B0 3FFF 1
            01B1 3FFF 1
            01B2 3FFF 1
            01B3 3FFF 1
            01B4 3FFF 1
            01B5 3FFF 1
            01B6 3FFF 1
            01B7 3FFF 1
            01B8 3FFF 1
            01B9 3FFF 1
            01BA 3FFF 1
            01BB 3FFF 1
            01BC 3FFF 1
            01BD 3FFF 1
            01BE 3FFF 1
            01BF 3FFF 1
            01C0 3FFF 1
            01C1 3FFF 1
            01C2 3FFF 1
            01C3 3FFF 1
            01C4 3FFF 1
            01C5 3FFF 1
            01C6 3FFF 1
            01C7 3FFF 1
            01C8 3FFF 1
            01C9 3FFF 1
            01CA 3FFF 1
            01CB 3FFF 1
            01CC 3FFF 1
            01CD 3FFF 1
            01CE 3FFF 1
            01CF 3FFF 1
            01D0 3FFF 1
            01D1 3FFF 1
            01D2 3FFF 1
            01D3 3FFF 1
            01D4 3FFF 1
            01D5 3FFF 1
            01D6 3FFF 1
            01D7 3FFF 1
            01D8 3FFF 1
            01D9 3FFF 1
            01DA 3FFF 1
            01DB 3FFF 1
            01DC 3FFF 1
            01DD 3FFF 1
            01DE 3FFF 1
            01DF 3FFF 1
            01E0 3FFF 1
            01E1 3FFF 1
            01E2 3FFF 1
            01E3 3FFF 1
            01E4 3FFF 1
            01E5 3FFF 1
            01E6 3FFF 1
            01E7 3FFF 1
            01E8 3FFF 1
            01E9 3FFF 1
            01EA 3FFF 1
            01EB 3FFF 1
            01EC 3FFF 1
            01ED 3FFF 1
            01EE 3FFF 1
            01EF 3FFF 1
            01F0 3FFF 1
            01F1 3FFF 1
            01F2 3FFF 1
            01F3 3FFF 1
            01F4 3FFF 1
            01F5 3FFF 1
            01F6 3FFF 1
            01F7 3FFF 1
            01F8 3FFF 1
            01F9 3FFF 1
            01FA 3FFF 1
            01FB 3FFF 1
            01FC 3FFF 1
            01FD 3FFF 1
            01FE 3FFF 1
            01FF 3FFF 1
            0200 3FFF 1
            0201 3FFF 1
            0202 3FFF 1
            0203 3FFF 1
            0204 3FFF 1
            0205 3FFF 1
            0206 3FFF 1
            0207 3FFF 1
            0208 3FFF 1
            0209 3FFF 1
            020A 3FFF 1
            020B 3FFF 1
            020C 3FFF 1
            020D 3FFF 1
            020E 3FFF 1
            020F 3FFF 1
            0210 3FFF 1
            0211 3FFF 1
            0212 3FFF 1
            0213 3FFF 1
            0214 3FFF 1
            0215 3FFF 1
            0216 3FFF 1
            0217 3FFF 1
            0218 3FFF 1
            0219 3FFF 1
            021A 3FFF 1
            021B 3FFF 1
            021C 3FFF 1
            021D 3FFF 1
            021E 3FFF 1
            021F 3FFF 1
            0220 3FFF 1
            0221 3FFF 1
            0222 3FFF 1
            0223 3FFF 1
            0224 3FFF 1
            0225 3FFF 1
            0226 3FFF 1
            0227 3FFF 1
            0228 3FFF 1
            0229 3FFF 1
            022A 3FFF 1
            022B 3FFF 1
            022C 3FFF 1
            022D 3FFF 1
            022E 3FFF 1
            022F 3FFF 1
            0230 3FFF 1
            0231 3FFF 1
            0232 3FFF 1
            0233 3FFF 1
            0234 3FFF 1
            0235 3FFF 1
            0236 3FFF 1
            0237 3FFF 1
            0238 3FFF 1
            0239 3FFF 1
            023A 3FFF 1
            023B 3FFF 1
            023C 3FFF 1
            023D 3FFF 1
            023E 3FFF 1
            023F 3FFF 1
            0240 3FFF 1
            0241 3FFF 1
            0242 3FFF 1
            0243 3FFF 1
            0244 3FFF 1
            0245 3FFF 1
            0246 3FFF 1
            0247 3FFF 1
            0248 3FFF 1
            0249 3FFF 1
            024A 3FFF 1
            024B 3FFF 1
            024C 3FFF 1
            024D 3FFF 1
            024E 3FFF 1
            024F 3FFF 1
            0250 3FFF 1
            0251 3FFF 1
            0252 3FFF 1
            0253 3FFF 1
            0254 3FFF 1
            0255 3FFF 1
            0256 3FFF 1
            0257 3FFF 1
            0258 3FFF 1
            0259 3FFF 1
            025A 3FFF 1
            025B 3FFF 1
            025C 3FFF 1
            025D 3FFF 1
            025E 3FFF 1
            025F 3FFF 1
            0260 3FFF 1
            0261 3FFF 1
            0262 3FFF 1
            0263 3FFF 1
            0264 3FFF 1
            0265 3FFF 1
            0266 3FFF 1
            0267 3FFF 1
            0268 3FFF 1
            0269 3FFF 1
            026A 3FFF 1
            026B 3FFF 1
            026C 3FFF 1
            026D 3FFF 1
            026E 3FFF 1
            026F 3FFF 1
            0270 3FFF 1
            0271 3FFF 1
            0272 3FFF 1
            0273 3FFF 1
            0274 3FFF 1
            0275 3FFF 1
            0276 3FFF 1
            0277 3FFF 1
            0278 3FFF 1
            0279 3FFF 1
            027A 3FFF 1
            027B 3FFF 1
            027C 3FFF 1
            027D 3FFF 1
            027E 3FFF 1
            027F 3FFF 1
            0280 3FFF 1
            0281 3FFF 1
            0282 3FFF 1
            0283 3FFF 1
            0284 3FFF 1
            0285 3FFF 1
            0286 3FFF 1
            0287 3FFF 1
            0288 3FFF 1
            0289 3FFF 1
            028A 3FFF 1
            028B 3FFF 1
            028C 3FFF 1
            028D 3FFF 1
            028E 3FFF 1
            028F 3FFF 1
            0290 3FFF 1
            0291 3FFF 1
            0292 3FFF 1
            0293 3FFF 1
            0294 3FFF 1
            0295 3FFF 1
            0296 3FFF 1
            0297 3FFF 1
            0298 3FFF 1
            0299 3FFF 1
            029A 3FFF 1
            029B 3FFF 1
            029C 3FFF 1
            029D 3FFF 1
            029E 3FFF 1
            029F 3FFF 1
            02A0 3FFF 1
            02A1 3FFF 1
            02A2 3FFF 1
            02A3 3FFF 1
            02A4 3FFF 1
            02A5 3FFF 1
            02A6 3FFF 1
            02A7 3FFF 1
            02A8 3FFF 1
            02A9 3FFF 1
            02AA 3FFF 1
            02AB 3FFF 1
            02AC 3FFF 1
            02AD 3FFF 1
            02AE 3FFF 1
            02AF 3FFF 1
            02B0 3FFF 1
            02B1 3FFF 1
            02B2 3FFF 1
            02B3 3FFF 1
            02B4 3FFF 1
            02B5 3FFF 1
            02B6 3FFF 1
            02B7 3FFF 1
            02B8 3FFF 1
            02B9 3FFF 1
            02BA 3FFF 1
            02BB 3FFF 1
            02BC 3FFF 1
            02BD 3FFF 1
            02BE 3FFF 1
            02BF 3FFF 1
            02C0 3FFF 1
            02C1 3FFF 1
            02C2 3FFF 1
            02C3 3FFF 1
            02C4 3FFF 1
            02C5 3FFF 1
            02C6 3FFF 1
            02C7 3FFF 1
            02C8 3FFF 1
            02C9 3FFF 1
            02CA 3FFF 1
            02CB 3FFF 1
            02CC 3FFF 1
            02CD 3FFF 1
            02CE 3FFF 1
            02CF 3FFF 1
            02D0 3FFF 1
            02D1 3FFF 1
            02D2 3FFF 1
            02D3 3FFF 1
            02D4 3FFF 1
            02D5 3FFF 1
            02D6 3FFF 1
            02D7 3FFF 1
            02D8 3FFF 1
            02D9 3FFF 1
            02DA 3FFF 1
            02DB 3FFF 1
            02DC 3FFF 1
            02DD 3FFF 1
            02DE 3FFF 1
            02DF 3FFF 1
            02E0 3FFF 1
            02E1 3FFF 1
            02E2 3FFF 1
            02E3 3FFF 1
            02E4 3FFF 1
            02E5 3FFF 1
            02E6 3FFF 1
            02E7 3FFF 1
            02E8 3FFF 1
            02E9 3FFF 1
            02EA 3FFF 1
            02EB 3FFF 1
            02EC 3FFF 1
            02ED 3FFF 1
            02EE 3FFF 1
            02EF 3FFF 1
            02F0 3FFF 1
            02F1 3FFF 1
            02F2 3FFF 1
            02F3 3FFF 1
            02F4 3FFF 1
            02F5 3FFF 1
            02F6 3FFF 1
            02F7 3FFF 1
            02F8 3FFF 1
            02F9 3FFF 1
            02FA 3FFF 1
            02FB 3FFF 1
            02FC 3FFF 1
            02FD 3FFF 1
            02FE 3FFF 1
            02FF 3FFF 1
            0300 3FFF 1
            0301 3FFF 1
            0302 3FFF 1
            0303 3FFF 1
            0304 3FFF 1
            0305 3FFF 1
            0306 3FFF 1
            0307 3FFF 1
            0308 3FFF 1
            0309 3FFF 1
            030A 3FFF 1
            030B 3FFF 1
            030C 3FFF 1
            030D 3FFF 1
            030E 3FFF 1
            030F 3FFF 1
            0310 3FFF 1
            0311 3FFF 1
            0312 3FFF 1
            0313 3FFF 1
            0314 3FFF 1
            0315 3FFF 1
            0316 3FFF 1
            0317 3FFF 1
            0318 3FFF 1
            0319 3FFF 1
            031A 3FFF 1
            031B 3FFF 1
            031C 3FFF 1
            031D 3FFF 1
            031E 3FFF 1
            031F 3FFF 1
            0320 3FFF 1
            0321 3FFF 1
            0322 3FFF 1
            0323 3FFF 1
            0324 3FFF 1
            0325 3FFF 1
            0326 3FFF 1
            0327 3FFF 1
            0328 3FFF 1
            0329 3FFF 1
            032A 3FFF 1
            032B 3FFF 1
            032C 3FFF 1
            032D 3FFF 1
            032E 3FFF 1
            032F 3FFF 1
            0330 3FFF 1
            0331 3FFF 1
            0332 3FFF 1
            0333 3FFF 1
            0334 3FFF 1
            0335 3FFF 1
            0336 3FFF 1
            0337 3FFF 1
            0338 3FFF 1
            0339 3FFF 1
            033A 3FFF 1
            033B 3FFF 1
            033C 3FFF 1
            033D 3FFF 1
            033E 3FFF 1
            033F 3FFF 1
            0340 3FFF 1
            0341 3FFF 1
            0342 3FFF 1
            0343 3FFF 1
            0344 3FFF 1
            0345 3FFF 1
            0346 3FFF 1
            0347 3FFF 1
            0348 3FFF 1
            0349 3FFF 1
            034A 3FFF 1
            034B 3FFF 1
            034C 3FFF 1
            034D 3FFF 1
            034E 3FFF 1
            034F 3FFF 1
            0350 3FFF 1
            0351 3FFF 1
            0352 3FFF 1
            0353 3FFF 1
            0354 3FFF 1
            0355 3FFF 1
            0356 3FFF 1
            0357 3FFF 1
            0358 3FFF 1
            0359 3FFF 1
            035A 3FFF 1
            035B 3FFF 1
            035C 3FFF 1
            035D 3FFF 1
            035E 3FFF 1
            035F 3FFF 1
            0360 3FFF 1
            0361 3FFF 1
            0362 3FFF 1
            0363 3FFF 1
            0364 3FFF 1
            0365 3FFF 1
            0366 3FFF 1
            0367 3FFF 1
            0368 3FFF 1
            0369 3FFF 1
            036A 3FFF 1
            036B 3FFF 1
            036C 3FFF 1
            036D 3FFF 1
            036E 3FFF 1
            036F 3FFF 1
            0370 3FFF 1
            0371 3FFF 1
            0372 3FFF 1
            0373 3FFF 1
            0374 3FFF 1
            0375 3FFF 1
            0376 3FFF 1
            0377 3FFF 1
            0378 3FFF 1
            0379 3FFF 1
            037A 3FFF 1
            037B 3FFF 1
            037C 3FFF 1
            037D 3FFF 1
            037E 3FFF 1
            037F 3FFF 1
            0380 3FFF 1
            0381 3FFF 1
            0382 3FFF 1
            0383 3FFF 1
            0384 3FFF 1
            0385 3FFF 1
            0386 3FFF 1
            0387 3FFF 1
            0388 3FFF 1
            0389 3FFF 1
            038A 3FFF 1
            038B 3FFF 1
            038C 3FFF 1
            038D 3FFF 1
            038E 3FFF 1
            038F 3FFF 1
            0390 3FFF 1
            0391 3FFF 1
            0392 3FFF 1
            0393 3FFF 1
            0394 3FFF 1
            0395 3FFF 1
            0396 3FFF 1
            0397 3FFF 1
            0398 3FFF 1
            0399 3FFF 1
            039A 3FFF 1
            039B 3FFF 1
            039C 3FFF 1
            039D 3FFF 1
            039E 3FFF 1
            039F 3FFF 1
            03A0 3FFF 1
            03A1 3FFF 1
            03A2 3FFF 1
            03A3 3FFF 1
            03A4 3FFF 1
            03A5 3FFF 1
            03A6 3FFF 1
            03A7 3FFF 1
            03A8 3FFF 1
            03A9 3FFF 1
            03AA 3FFF 1
            03AB 3FFF 1
            03AC 3FFF 1
            03AD 3FFF 1
            03AE 3FFF 1
            03AF 3FFF 1
            03B0 3FFF 1
            03B1 3FFF 1
            03B2 3FFF 1
            03B3 3FFF 1
            03B4 3FFF 1
            03B5 3FFF 1
            03B6 3FFF 1
            03B7 3FFF 1
            03B8 3FFF 1
            03B9 3FFF 1
            03BA 3FFF 1
            03BB 3FFF 1
            03BC 3FFF 1
            03BD 3FFF 1
            03BE 3FFF 1
            03BF 3FFF 1
            03C0 3FFF 1
            03C1 3FFF 1
            03C2 3FFF 1
            03C3 3FFF 1
            03C4 3FFF 1
            03C5 3FFF 1
            03C6 3FFF 1
            03C7 3FFF 1
            03C8 3FFF 1
--- everything after this are just more 3FFF ---

I still had the same issue when parsing at the rising edge, but it looks fine and matches the decrypted PDK if sampling on the falling edge.

Commands, unlike sampling at the falling edge at 2MHz, also are properly detected.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 26, 2018, 11:14:10 am
Nope, after analyzing properly the .bin being read back I'm still getting one bit offs. I've attached the correct .bin and the two .bins read on falling and rising edges  :palm:

I'm also attaching the latest version of my parsing tools. "parsespivdd.py" is the script that converts the TXTs from Zeroplus to a series of frames, in case somebody manages to make any sense of this mess.

Example:
Code: [Select]
./parsespivdd.py --txt verify_5mhz.txt --data PA6_ICPDA --clock PA3_ICPCK --enable VDD --falling | tee verify_5mhz_frames_falling.txtRemove --falling to sample on the rising edge.

parsecommands.py has no options:
Code: [Select]
cat verify_5mhz_frames_falling.txt | ./parsecommands.py
EDIT: It looks like this could be still too slow for correct sampling:
(https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/?action=dlattach;attach=605575)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 26, 2018, 06:12:39 pm
Nope, after analyzing properly the .bin being read back I'm still getting one bit offs. I've attached the correct .bin and the two .bins read on falling and rising edges  :palm:

EDIT: It looks like this could be still too slow for correct sampling:
(https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/?action=dlattach;attach=605575)

Hi,

thanks for your hard work.

I don't think that the sampling frequency is the problem. Each clock cycle is clearly >=5 time cycles which implies that the real clock used is indeed 1 MHz only.

One possibility could be that you might need to add a delay before taking the sample:
e.g. CLK goes high, take the value from *next* sample for DAT. But this is very uncommon.

I also thought about the "garbage" bits in reads. From what I remember from the calibration routine:
It could be that this is an ACK from WRITER. So after IC sent out some bits, direction is changed and IC waits for signal from host. Either just a clock or clock+value (so sampling edge might change for this bit again).

I will be away from my WRITER/LogicAnalyzer for the next few days, participating 35C3. Anybody there? PM me if you like to meet.

JS
 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 26, 2018, 06:22:29 pm
One big problem is to capture the output image. Right now I print it to PDF or just take a screenshot from browser.
I plan to automate this by adding a canvas capture and save to image function later.

When all is fixed I will release the generator on github.

Sounds good. Please add SVG output as well, or let me know when you are done and I can add it, because then I can just insert it in Open Office documents without bitmap quality loss.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 27, 2018, 01:28:38 am
I have been able to extract 1:1 the binary from Verify_5MHz.txt by using a weird trick, instead of sampling at rising or falling edge.

For each clock cycle, I output a one if the data pin is high for at least one sample while the clock pin is high. Otherwise, I output a zero. This seems to work just fine for both data and commands.

However, I am not sure why would this work - I don't see why would anybody use something so convoluted as a "level-sensitive" latch for communication (specially since I doubt that would help them lower costs).

I can only think that there must be some jitter somewhere trashing the experiment (which would also explain why the clock is so iregular - a bitbanged SPI using a "while" loop wouldn't certainly do that!)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on December 27, 2018, 02:21:36 am
My guess would be the programmer's bitbang code changes the data right before setting the clock, and uses a software loop to limit the frequency.

The sample rate of the logic analyzer is fast enough to see all clocks, but maybe not enough to consistently get the short delay between changing of data and rising of clock.

A hardware shift register should have a setup time in the ns range, so the target MCU reads nicely.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 27, 2018, 06:02:31 pm
The voltage levels look suspiciously like zener voltages.

Could it be that they are 2.7V, 5.6V and 8.2V upon closer inspection?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 28, 2018, 11:05:30 am
The voltage levels look suspiciously like zener voltages.

Could it be that they are 2.7V, 5.6V and 8.2V upon closer inspection?

Nice catch.

This also brought to my attention that the singal voltage might be smaller than standard TTL and this might require setting a lower trigger level in logic analyzer ( http://www.zeroplus.com.tw/logic-analyzer_en/faq_hardware.php (http://www.zeroplus.com.tw/logic-analyzer_en/faq_hardware.php) ).

With the wrong (to high) trigger level (from TTL) it would explain why the signal is not captured 100% correctly especially with clock rates >=1 MHz.

When I'm back I will try to make a new capture with lower trigger level.

Nevertheless we should have all the information now to start writing down a draft of the flashing protocol and start with some experiments,

Anybody has a an idea how to create a cheap circuit to create different voltages (12V / 8.5V / 6.5 V / 5V / 3V ...) based on MCU output (using some digital outputs).

Have fun,

JS
 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 28, 2018, 11:21:59 am
Anybody has a an idea how to create a cheap circuit to create different voltages (12V / 8.5V / 6.5 V / 5V / 3V ...) based on MCU output (using some digital outputs).

This would be easy, just a LM317 and 2 resistors per voltage (and a decoupling capacitor). Then maybe some FETs to switch the output on and off, if it needs more power than a 4051 multiplexer can do.

For the construction I would do it the way PICkit and other programmers work:

(https://images-na.ssl-images-amazon.com/images/I/51JJF3CShXL._SX342_.jpg)

Just the required programming signals on a pinheader on a small device. This could be plugged into any adapter etc. someone wants.

Meanwhile I got one channel of my ADC working. I can now sample with 8 bit resolution, -10 V to +10 V, and 25 MHz samplerate:

https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2073310/#msg2073310 (https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2073310/#msg2073310)

Will solder the other 3 channels and finish the FPGA programming, then I can record a full programming cycle, with 25 MHz sampling rate for all 4 channels, and optionally 8 channels with a second board and still 25 MHz, if the bandwidth to the DDR3 RAM works out. Even if we don't need it anymore, was still fun to build it :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 28, 2018, 11:41:32 am

This would be easy, just a LM317 and 2 resistors per voltage (and a decoupling capacitor). Then maybe some FETs to switch the output on and off, if it needs more power than a 4051 multiplexer can do.

Can you draw a small schematic of this so i can assemble it on a bread board? I'm not so good with building circuits...

I have some 74HC4050 and CD4007UBE for signal level shifting (either up or down, just as we need for input/output of digital signals from MCU to/from IC).

Meanwhile I got one channel of my ADC working. I can now sample with 8 bit resolution, -10 V to +10 V, and 25 MHz samplerate:

https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2073310/#msg2073310 (https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2073310/#msg2073310)

Will solder the other 3 channels and finish the FPGA programming, then I can record a full programming cycle, with 25 MHz sampling rate for all 4 channels, and optionally 8 channels with a second board and still 25 MHz, if the bandwidth to the DDR3 RAM works out. Even if we don't need it anymore, was still fun to build it :)

I'm very interested in this project and would love to see a 1GByte 8 channel analog logic analyzer :-) If it works good I will get / build one for sure.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 28, 2018, 03:18:35 pm
The 74HC4050 looks good when the microcontroller wants to send back data, e.g. for the verify cycle.

I don't know much either about analog circuits, but I think it is called high-side switch what we would need, like this:

http://cq.cx/interface.pl#13 (http://cq.cx/interface.pl#13)

I tried to simulate it in LTSpice, but it switches really slow:

(https://i.imgur.com/t89M68b.png)

If I reduce R3 to 100 ohm, it gets better, but then the transistor Q1 might get very warm. There are all in one ICs as well for high side switches, but not as fun as DIY :)

For the voltage regulator, just look at the datasheet of the LM317 (https://www.st.com/content/ccc/resource/technical/document/datasheet/8e/b2/ea/56/ad/8c/43/d8/CD00000549.pdf/files/CD00000549.pdf/jcr:content/translations/en.CD00000549.pdf), figure 3, and the formula for R1 and R2 in chapter 6. It works up to 37 V, but it is a linear regulator, so it gets hot when the programmed IC needs much power (e.g. supply voltage is 20 V, you want 8 V output, and with 100 mA, then 12 V * 0.1 A = 1.2 W is dissipated in heat at the regulator). But should be fine with a 12 V power supply to generate all voltages. Could be generated with a step-up converter, so that it would work with a 5 V USB power supply, or even from the USB port, if it doesn't need much power.

I think first we should measure the required currents and the required timings. Then we could design the programmer circuit. I guess it doesn't matter if it needs like 100 us to turn on a higher voltage for VPP with a relatively high current. We could use a few of these high side switches to select different voltages. But then for the logic signals, which might need only uA, we could use 4051 multiplexers to switch the VPP signal to and from the logic inputs very fast.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 28, 2018, 03:20:10 pm
Attached is the LTspice simulation for the high-side switch.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 03:21:49 pm
I was thinking about putting some zener diodes in parallel and switching them with an uln2003.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 28, 2018, 03:38:08 pm
The ULN2003 switches to GND. But if it the IC needs just a few milliampere, the LM317 etc. might be overkill, and you could use a zener diode, and then just pull it low with a ULN2003, and wire-or the different voltages with more diodes. But wouldn't be very accurate and wasting some power. I think my solution would cost like EUR 2 per voltage.

Another idea would be to use a cheap DAC and OpAmp to control the voltage. This would allow any voltage without a voltage regulator (but a reference voltage IC for the DAC), and would be even cheaper.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 03:44:06 pm
The ULN2003 switches to GND.

Exactly. Zener on top, ULN switch on the bottom. ULN on -> current flows through the zener reducing the voltage to the IC to that value. Input voltage cant be to high obviously ;) but there could be a pull-down resistor in parallel with the zeners also switched with the uln2003 to limit the voltage to something safe.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 03:50:12 pm
And if the current isnt to high the uln2003 could be replaced with the output pin of a microcontroller.
~20 mA.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on December 28, 2018, 04:05:40 pm
You could use low output to enable and Z to disable a zener, except you will have a voltage swing limit due to the clamping diodes on every GPIO.

If you use a 3.3V microcontroller and have a 3.0V zener for the outputs then it will max your voltage output at 3.3 + 0.7 + 3.0. You will not be able to get 12V from this circuit.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on December 28, 2018, 04:17:33 pm
TPIC6C595 is a nice upgrade from the old ULN2003. The DMOS outputs get close to ground (the darlingtons in the ULN only go down to about 1V) and it only requires only 3 GPIO from the microcontroller. The only thing I don't like about it is that it is a 5V part.

http://www.ti.com/lit/ds/symlink/tpic6c595.pdf (http://www.ti.com/lit/ds/symlink/tpic6c595.pdf)

TPIC6B595 and TPIC6A595 have lower Rdson, so they can handle a bit more current.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 04:21:26 pm
You have to power the micro anyway.
So my thinking was to use 12v standard supply and then reduce the voltage to the appropriate level using the zeners.
As the uln2003 (or micro) switches to gnd that shouldnt be a problem.

I ordered some  ULN2003V12S16-13 a while back, was thinking of using those when they arrive.
They're 3.3V compatible.

Somewhat like this:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 28, 2018, 07:59:30 pm
For generating VDD and VPP I'd just use any random linear regulator, with NMOS for switching the divider resistor, one for each pin.

I think it should be even possible to remove the NMOS altogether, using GPIO from the programming microcontroller and switching between high impedance and open collector, given how little current this draws.

I think it would be even possible to drive VDD straight from 3.3V or 5V (with another MOSFET for switching on and off), and thus have the regulator for switching between 5.6/8.2V only on the VPP pin.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 08:10:17 pm
For generating VDD and VPP I'd just use any random linear regulator, with NMOS for switching the divider resistor, one for each pin.

I dont know how fast the voltage transitions have to be.
From the pictures in Davids video they seem to be rather fast.
Voltage regulators typically have settling times that are rather long.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 28, 2018, 08:26:05 pm
For generating VDD and VPP I'd just use any random linear regulator, with NMOS for switching the divider resistor, one for each pin.

I dont know how fast the voltage transitions have to be.
From the pictures in Davids video they seem to be rather fast.
Voltage regulators typically have settling times that are rather long.
They're not that fast, you can actually see it settling on the Verify file that was uploaded with the analog Vpp.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 28, 2018, 09:06:18 pm
It would be nice to have the feature to set any voltage from 2.0V to 12.0V

2.0V - 5.0V are needed for calibration later (at least with 0.1V steps).

6.5, 8.5, 12.0 are needed for programing (OTP need higer voltages).

I was looking at something like PWM output and LM371T but the refernce schematic looks big (lots of components and an opamp).

JS

The voltage is not changed very often. The trace from Dave just showed that no capacitator was used to stabelize the vdd voltage...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 28, 2018, 09:18:06 pm
It would be nice to have the feature to set any voltage from 2.0V to 12.0V

Then maybe this would be something to look at:
http://openprog.altervista.org/OP_eng.html#Regulator (http://openprog.altervista.org/OP_eng.html#Regulator)
boost converter with feedback by using only a microcontroller

And for lower voltages you can just do pwm.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 28, 2018, 09:21:57 pm
2.0V - 5.0V are needed for calibration later (at least with 0.1V steps).
How is that? What are those used for?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 29, 2018, 12:03:50 am
2.0V - 5.0V are needed for calibration later (at least with 0.1V steps).
How is that? What are those used for?
After writing the firmware, the IC can be calibrated. Due to manufacturing differences the internal clock might need some tuning (up or down) to produce the exact desired frequency of e.g. 16MHz. This also depends on the supply voltage (VDD). So if you plan to use the IC with 3.1V later you need to calibrate it using 3.1V for VDD. Calibration itself is a very simple process. You just let the IC run a loop with e.g. 5000000 cycles, The IC outputs a signal when it starts and when it finishs. The flasher captures the time it took and then can increase or decrease the clock a tiny tiny bit to calibrate it.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 29, 2018, 12:26:28 am
I was looking at something like PWM output and LM371T but the refernce schematic looks big (lots of components and an opamp).

The basic circuit is simple, and at least in LTspice it works:

(https://i.imgur.com/0uFPbRv.png)

The 0-3 V is translated to 0-9 V. The 2SCR542P transistor is really nice: can switch up to 5 A, with a beefy TO-243 package and costs only 56 cent at Digikey.

To generate the 0-3 V control voltage, you could use a cheap DAC, like the MCP4901. Together with a reference voltage IC, like the LM4040, it should be pretty accurate without calibration.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 29, 2018, 03:12:33 pm
Many thanks for all your suggestions but it still looks complicated to me.

After searching around and considering my limited electronics skills I came up with this idea:

LM317 (adjustable ldo, approx USD 0.5)
MCP4141 (digital potentiometer, approx USD 0.7))
2 caps, 1 resistor

Would this work? For sure is easy to assemble  :).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on December 29, 2018, 03:53:00 pm
The datasheet for the digital potentiometer says in the absolute maximum ratings table: "Voltage on all other pins (PxA, PxW, PxB..." = -0.3 V to Vdd + 0.3 V. Recommended max supply voltage for Vdd is 5.5 V. This means at the potentiometer pins you can use max 5.8 V, and probably it won't work at all for voltages > Vdd.

But my solution doesn't look too complicated. You can get all chips in DIP as well, and the LM4040 voltage reference in TO92-3 (looks like a transistor) for easier testing on a breadboard (the 3 V version of the reference would be the right choice, if the microcontroller and DAC runs with 3.3 V). For the OpAmp anything should do it, like a LM324, if you don't need to go to 0 V (it is not a rail-to-rail OpAmp). But might need some extra calibration. The ADA4522 has low offset voltage and low drift, which means it would be very accurate relatively to the voltage reference without calibration. I would just design a PCB for it and then use all SMD parts, it is actually easier to solder and would be a nice compact module.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 29, 2018, 03:58:06 pm
You could also do a variation of
http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits (http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits)
look for "Adjustable regulator with digitally selected output"

Replace the transistors with a ULN2003.
I think they cost USD 0.15 plus a few resistors.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 29, 2018, 04:20:21 pm
You could also do a variation of
http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits (http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits)
look for "Adjustable regulator with digitally selected output"

Replace the transistors with a ULN2003.
I think they cost USD 0.15 plus a few resistors.
That's exactly what I thought about in my previous post, but that won't work if you also need to calibrate it running from 3 to 5V. It may work if you don't really give a damn about calibrating and use it only for programming, or allow calibrating only at preset voltages (which to be honest, would be the case - aside from 3.3, 3.6 and 5V, who really needs any other voltages?)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 29, 2018, 04:58:47 pm
You could also do a variation of
http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits (http://www.circuitstoday.com/few-lm317-voltage-regulator-circuits)
look for "Adjustable regulator with digitally selected output"

Replace the transistors with a ULN2003.
I think they cost USD 0.15 plus a few resistors.
That's exactly what I thought about in my previous post, but that won't work if you also need to calibrate it running from 3 to 5V. It may work if you don't really give a damn about calibrating and use it only for programming, or allow calibrating only at preset voltages (which to be honest, would be the case - aside from 3.3, 3.6 and 5V, who really needs any other voltages?)

No, no. You can choose the resistor values as you want and also switch them in parallel, kind of like a digital potentiometer (but they usually have the resistors in series).
1/R = 1/R1 + 1/R2 + ...
One would have to figure out the appropriate values though...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 29, 2018, 05:13:50 pm
Yeah, if you're doing that you'd better switch them in parallel, because the moment you leave none connected (ie when switching from one to the other) you're gonna pass the full voltage to the output  ;D

For regulating, you probably want to use the resistors as a rudimentary R2R ladder. For having 0.1V range from 2 to 5V you'll need ceil(log2((5-2)/0.1))=5 resistors, which aren't too many.

EDIT: I think this is slightly too overkill - we'll need probably 5 precision resistors with non-standard values, or five pots. I think just using a LM317 and a DAC as an offset for its ground should work better.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: iMo on December 29, 2018, 07:46:11 pm
You may consider a PWM DAC - below one gives you almost any Vout from 0-12V.
You may set the upper range by R2/R3, here

Vmax = 3.3V*(1+R2/R3), where 3.3V is MCUs log1

and the actual voltage by setting the PWM duty. The higher the PWM freq the faster settling with smaller R1C1.
Example only.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 30, 2018, 08:31:43 am
You may consider a PWM DAC - below one gives you almost any Vout from 0-12V.

Nice.

Going along those lines: (Voltage Regulator Control with DAC) -> Actually describes using PWM to control a voltage regulator
https://www.microchip.com/forums/FindPost/985974 (https://www.microchip.com/forums/FindPost/985974)

If the output voltage is sampled with an ADC there's no need for an opamp (or precision ;) and transients would be handled by the voltage regulator.

I wonder if a fixed voltage regulator could be used by modifying the current/voltage on the GND lead. (I know that putting zeners there shift the output voltage)

EDIT: seems that you can easily:
https://electronicsforu.com/electronics-projects/hardware-diy/variable-power-supply-using-fixed-voltage-regulator-ic (https://electronicsforu.com/electronics-projects/hardware-diy/variable-power-supply-using-fixed-voltage-regulator-ic)

Makes it very cheap SC1117-3.3V regulators cost less than USD 0.03

But cant go lower than the fixed voltage apparently :(
Also adjustable regulators of the same kind also cost less than USD 0.03 :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 30, 2018, 01:11:03 pm
Just use a normal adjustable regulator, such as the LM317 (1.25V reference) or LM431 (2.5V reference). They're less than 0.10$ a piece in TO-92.

IMHO I think we're trying to overdesign this. Having just a set of common reference voltages for VDD should work for calibrating - after all, if you really want a somewhat stable clock (as it'll also drift from temperature changes), you'll use a regulated power supply at a standard voltage such as 3.3V or 5V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 30, 2018, 06:31:54 pm
Attached is the design I'd use for Vdd.

I'm using a HT7133 because it's a cheap linear regulator, it's available in TO92 for easy prototyping, and has a Vref of 3.3 which means you can buy many for using as 3.3V regulator with no resistors in other circuits.

The 200ohm resistor must be that value our lower, to ensure there are always 10mA of current being consumed -the minimum according to datasheet- any moment to ensure the regulator doesn't output a voltage higher than designed.

I'd try if the Padauk ICs can use 3.3V in place of 2.6V (used in non-RW operations and during command transmission) and 5V in place of 4.3V (used during flash reads), since that would make everything much easier. Otherwise m we would probably need to put a DAC for more accurate control, as I'm not sure adding more and more resistors scale.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 30, 2018, 09:43:53 pm
I did a new capture of VERIFY.

This time I lowered the voltage to detect a 1 down to 1.2V (was 1.5V).
I also found a way to capture the complete VERIFY command at 200MHz (the logic analyzer has a compression feature).
This messed up my trigger a bit (you see the scanning spikes before and after the command, which are used by writer to detect IC presence).
I hope now we can read the signal 100% ok without any tricks.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 31, 2018, 01:39:28 am
I did a new capture of VERIFY.

This time I lowered the voltage to detect a 1 down to 1.2V (was 1.5V).
I also found a way to capture the complete VERIFY command at 200MHz (the logic analyzer has a compression feature).
This messed up my trigger a bit (you see the scanning spikes before and after the command, which are used by writer to detect IC presence).
I hope now we can read the signal 100% ok without any tricks.

JS

When sampling on rising edge now:
Code: [Select]
116050251: FLASH_READ_B
    No data (dummy read)

 121460163: FLASH_READ_B

    ADDR DATA ?
    -----------
    07EF 1FFE 0
    07F0 0025 0
    07F1 0025 1

 125171746: ??? (1010010110100101101001011010001100001010101000010)

 132819271: ??? (1010010110100101101001011010011001101010101000010)

 189653978: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07F0 0026 3FFF 3FFF 3FFF


 194375712: FLASH_READ_B

    ADDR DATA ?
    -----------
    07F0 0026 0

 198033461: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07F0 3FFF 0026 3FFF 3FFF


 202755194: FLASH_READ_B

    ADDR DATA ?
    -----------
    07F1 0002 1

 206415006: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0002 0
    07F1 0002 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1FFF 1
    07F9 1FFF 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 1FFF 1
    07FF 1FFF 1

 210876950: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1FFF 1
    07F9 1FFF 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 1FFF 1
    07FF 1FFF 1

 216360622: FLASH_READ_B

    ADDR DATA ?
    -----------
    0000 1FFF 0
    0001 1FFF 0
    0002 1FFF 1
    0003 1FFF 1
    0004 1FFF 1
    0005 1FFF 1
    0006 1FFF 1
    0007 1FFF 1
    0008 1FFF 1
    0009 1FFF 1
    000A 1FFF 1
    000B 1FFF 1
    000C 1FFF 1
    000D 1FFF 1
    000E 1FFF 1
    000F 1FFF 1
    0010 1FFF 1
    0011 1FFF 1
    0012 1FFF 1
    0013 1FFF 1
    0014 1FFF 1
    0015 1FFF 1
    0016 1FFF 1
    0017 1FFF 1
    0018 1FFF 1
    0019 1FFF 1
    001A 1FFF 1
    001B 1FFF 1
    001C 1FFF 1
    001D 1FFF 1
    001E 1FFF 1
    001F 1FFF 1
    0020 1FFF 1
    0021 1FFF 1
    0022 1FFF 1
    0023 1FFF 1
    0024 1FFF 1
    0025 1FFF 1
    0026 1FFF 1
    0027 1FFF 1
    0028 1FFF 1
    0029 1FFF 1
    002A 1FFF 1
    002B 1FFF 1
    002C 1FFF 1
    002D 1FFF 1
    002E 1FFF 1
    002F 1FFF 1
    0030 1FFF 1
    0031 1FFF 1
    0032 1FFF 1
    0033 1FFF 1
    0034 1FFF 1
    0035 1FFF 1
    0036 1FFF 1
    0037 1FFF 1
    0038 1FFF 1
    0039 1FFF 1
    003A 1FFF 1
    003B 1FFF 1
    003C 1FFF 1
    003D 1FFF 1
    003E 1FFF 1
    003F 1FFF 1
    0040 1FFF 1
    0041 1FFF 1
    0042 1FFF 1
    0043 1FFF 1
    0044 1FFF 1
    0045 1FFF 1
    0046 1FFF 1
    0047 1FFF 1
    0048 1FFF 1
    0049 1FFF 1
    004A 1FFF 1
    004B 1FFF 1
    004C 1FFF 1
    004D 1FFF 1
    004E 1FFF 1
    004F 1FFF 1
    0050 1FFF 1
    0051 1FFF 1
    0052 1FFF 1
    0053 1FFF 1
    0054 1FFF 1
    0055 1FFF 1
    0056 1FFF 1
    0057 1FFF 1
    0058 1FFF 1
    0059 1FFF 1
    005A 1FFF 1
    005B 1FFF 1
    005C 1FFF 1
    005D 1FFF 1
    005E 1FFF 1
    005F 1FFF 1
    0060 1FFF 1
    0061 1FFF 1
    0062 1FFF 1
    0063 1FFF 1
    0064 1FFF 1
    0065 1FFF 1
    0066 1FFF 1
    0067 1FFF 1
    0068 1FFF 1
    0069 1FFF 1
    006A 1FFF 1
    006B 1FFF 1
    006C 1FFF 1
    006D 1FFF 1
    006E 1FFF 1
    006F 1FFF 1
    0070 1FFF 1
    0071 1FFF 1
    0072 1FFF 1
    0073 1FFF 1
    0074 1FFF 1
    0075 1FFF 1
    0076 1FFF 1
    0077 1FFF 1
    0078 1FFF 1
    0079 1FFF 1
    007A 1FFF 1
    007B 1FFF 1
    007C 1FFF 1
    007D 1FFF 1
    007E 1FFF 1
    007F 1FFF 1
    0080 1FFF 1
    0081 1FFF 1
    0082 1FFF 1
    0083 1FFF 1
    0084 1FFF 1
    0085 1FFF 1
    0086 1FFF 1
    0087 1FFF 1
    0088 1FFF 1
    0089 1FFF 1
    008A 1FFF 1
    008B 1FFF 1
    008C 1FFF 1
    008D 1FFF 1
    008E 1FFF 1
    008F 1FFF 1
    0090 1FFF 1
    0091 1FFF 1
    0092 1FFF 1
    0093 1FFF 1
    0094 1FFF 1
    0095 1FFF 1
    0096 1FFF 1
    0097 1FFF 1
    0098 1FFF 1
    0099 1FFF 1
    009A 1FFF 1
    009B 1FFF 1
    009C 1FFF 1
    009D 1FFF 1
    009E 1FFF 1
    009F 1FFF 1
    00A0 1FFF 1
    00A1 1FFF 1
    00A2 1FFF 1
    00A3 1FFF 1
    00A4 1FFF 1
    00A5 1FFF 1
    00A6 1FFF 1
    00A7 1FFF 1
    00A8 1FFF 1
    00A9 1FFF 1
    00AA 1FFF 1
    00AB 1FFF 1
    00AC 1FFF 1
    00AD 1FFF 1
    00AE 1FFF 1
    00AF 1FFF 1
    00B0 1FFF 1
    00B1 1FFF 1
    00B2 1FFF 1
    00B3 1FFF 1
    00B4 1FFF 1
    00B5 1FFF 1
    00B6 1FFF 1
    00B7 1FFF 1
    00B8 1FFF 1
    00B9 1FFF 1
    00BA 1FFF 1
    00BB 1FFF 1
    00BC 1FFF 1
    00BD 1FFF 1
    00BE 1FFF 1
    00BF 1FFF 1
    00C0 1FFF 1
    00C1 1FFF 1
    00C2 1FFF 1
    00C3 1FFF 1
    00C4 1FFF 1
    00C5 1FFF 1
    00C6 1FFF 1
    00C7 1FFF 1
    00C8 1FFF 1
    00C9 1FFF 1
    00CA 1FFF 1
    00CB 1FFF 1
    00CC 1FFF 1
    00CD 1FFF 1
    00CE 1FFF 1
    00CF 1FFF 1
    00D0 1FFF 1
    00D1 1FFF 1
    00D2 1FFF 1
    00D3 1FFF 1
    00D4 1FFF 1
    00D5 1FFF 1
    00D6 1FFF 1
    00D7 1FFF 1
    00D8 1FFF 1
    00D9 1FFF 1
    00DA 1FFF 1
    00DB 1FFF 1
    00DC 1FFF 1
    00DD 1FFF 1
    00DE 1FFF 1
    00DF 1FFF 1
    00E0 1FFF 1
    00E1 1FFF 1
    00E2 1FFF 1
    00E3 1FFF 1
    00E4 1FFF 1
    00E5 1FFF 1
    00E6 1FFF 1
    00E7 1FFF 1
    00E8 1FFF 1
    00E9 1FFF 1
    00EA 1FFF 1
    00EB 1FFF 1
    00EC 1FFF 1
    00ED 1FFF 1
    00EE 1FFF 1
    00EF 1FFF 1
    00F0 1FFF 1
    00F1 1FFF 1
    00F2 1FFF 1
    00F3 1FFF 1
    00F4 1FFF 1
    00F5 1FFF 1
    00F6 1FFF 1
    00F7 1FFF 1
    00F8 1FFF 1
    00F9 1FFF 1
    00FA 1FFF 1
    00FB 1FFF 1
    00FC 1FFF 1
    00FD 1FFF 1
    00FE 1FFF 1
    00FF 1FFF 1
    0100 1FFF 1
    0101 1FFF 1
    0102 1FFF 1
    0103 1FFF 1
    0104 1FFF 1
    0105 1FFF 1
    0106 1FFF 1
    0107 1FFF 1
    0108 1FFF 1
    0109 1FFF 1
    010A 1FFF 1
    010B 1FFF 1
    010C 1FFF 1
    010D 1FFF 1
    010E 1FFF 1
    010F 1FFF 1
    0110 1FFF 1
    0111 1FFF 1
    0112 1FFF 1
    0113 1FFF 1
    0114 1FFF 1
    0115 1FFF 1
    0116 1FFF 1
    0117 1FFF 1
    0118 1FFF 1
    0119 1FFF 1
    011A 1FFF 1
    011B 1FFF 1
    011C 1FFF 1
    011D 1FFF 1
    011E 1FFF 1
    011F 1FFF 1
    0120 1FFF 1
    0121 1FFF 1
    0122 1FFF 1
    0123 1FFF 1
    0124 1FFF 1
    0125 1FFF 1
    0126 1FFF 1
    0127 1FFF 1
    0128 1FFF 1
    0129 1FFF 1
    012A 1FFF 1
    012B 1FFF 1
    012C 1FFF 1
    012D 1FFF 1
    012E 1FFF 1
    012F 1FFF 1
    0130 1FFF 1
    0131 1FFF 1
    0132 1FFF 1
    0133 1FFF 1
    0134 1FFF 1
    0135 1FFF 1
    0136 1FFF 1
    0137 1FFF 1
    0138 1FFF 1
    0139 1FFF 1
    013A 1FFF 1
    013B 1FFF 1
    013C 1FFF 1
    013D 1FFF 1
    013E 1FFF 1
    013F 1FFF 1
    0140 1FFF 1
    0141 1FFF 1
    0142 1FFF 1
    0143 1FFF 1
    0144 1FFF 1
    0145 1FFF 1
    0146 1FFF 1
    0147 1FFF 1
    0148 1FFF 1
    0149 1FFF 1
    014A 1FFF 1
    014B 1FFF 1
    014C 1FFF 1
    014D 1FFF 1
    014E 1FFF 1
    014F 1FFF 1
    0150 1FFF 1
    0151 1FFF 1
    0152 1FFF 1
    0153 1FFF 1
    0154 1FFF 1
    0155 1FFF 1
    0156 1FFF 1
    0157 1FFF 1
    0158 1FFF 1
    0159 1FFF 1
    015A 1FFF 1
    015B 1FFF 1
    015C 1FFF 1
    015D 1FFF 1
    015E 1FFF 1
    015F 1FFF 1
    0160 1FFF 1
    0161 1FFF 1
    0162 1FFF 1
    0163 1FFF 1
    0164 1FFF 1
    0165 1FFF 1
    0166 1FFF 1
    0167 1FFF 1
    0168 1FFF 1
    0169 1FFF 1
    016A 1FFF 1
    016B 1FFF 1
    016C 1FFF 1
    016D 1FFF 1
    016E 1FFF 1
    016F 1FFF 1
    0170 1FFF 1
    0171 1FFF 1
    0172 1FFF 1
    0173 1FFF 1
    0174 1FFF 1
    0175 1FFF 1
    0176 1FFF 1
    0177 1FFF 1
    0178 1FFF 1
    0179 1FFF 1
    017A 1FFF 1
    017B 1FFF 1
    017C 1FFF 1
    017D 1FFF 1
    017E 1FFF 1
    017F 1FFF 1
    [cut to keep message under 50k chars - they're all 1FFF anyway]
    07C0 1FFF 1
    07C1 1FFF 1
    07C2 1FFF 1
    07C3 1FFF 1
    07C4 1FFF 1
    07C5 1FFF 1
    07C6 1FFF 1
    07C7 1FFF 1
    07C8 1FFF 1
    07C9 1FFF 1
    07CA 1FFF 1
    07CB 1FFF 1
    07CC 1FFF 1
    07CD 1FFF 1
    07CE 1FFF 1
    07CF 1FFF 1
    07D0 1FFF 1
    07D1 1FFF 1
    07D2 1FFF 1
    07D3 1FFF 1
    07D4 1FFF 1
    07D5 1FFF 1
    07D6 1FFF 1
    07D7 1FFF 1
    07D8 1FFF 1
    07D9 1FFF 1
    07DA 1FFF 1
    07DB 1FFF 1
    07DC 1FFF 1
    07DD 1FFF 1
    07DE 1FFF 1
    07DF 1FFF 1

 274899016: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    0000 0070 2F00 0182 3FED
    0004 018B 3FEE 019A 2F80
    0008 019B 2F1C 0183 3FFE
    000C 2AFF 3054 3FED 0B81
    0010 1F91 2F05 0B80 1AD0
    0014 3013 1F90 0063 3016
    0018 1180 3016 1D90 18D0
    001C 301B 2F01 1950 2FFF
    0020 0C01 018B 0B81 1AD0
    0024 3023 1B50 304F 2F04
    0028 0188 18D0 3029 2F02
    002C 0182 1304 1305 2F6E
    0030 0B82 2F00 0B83 0006
    0034 0B04 0007 0805 1584
    0038 1685 1004 1282 1083
    003C 1A40 3033 1F90 1AD0
    0040 303F 1584 1685 0590
    0044 18D0 3044 1950 303F
    0048 1D90 1AD0 3049 18D0
    004C 304B 1B50 302B 18D0
    0050 304F 1B50 3011 3053
    0054 018B 1ED1 1ED0 2F03
    0058 0BC1 2F8A 0BC0 2F56
    005C 0063 305C 11C0 305C
    0060 11C1 305C 1CD0 2F03
    0064 0BC1 2F8A 0BC0 2F56
    0068 0063 3068 11C0 3068
    006C 11C1 3068 3056 3FFF


 282886516: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 02FF 31FD


 290648067: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1850 1
    07F9 1F54 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 02FF 1
    07FF 11FD 1

 296125972: FLASH_READ_B

    ADDR DATA ?
    -----------
    0000 0070 0
    0001 0F00 0
    0002 0182 0
    0003 1FED 0
    0004 018B 0
    0005 1FEE 1
    0006 019A 0
    0007 0F80 1
    0008 019B 0
    0009 0F1C 0
    000A 0183 0
    000B 1FFE 0
    000C 0AFF 0
    000D 1054 1
    000E 1FED 0
    000F 0B81 1
    0010 1F91 1
    0011 0F05 0
    0012 0B80 1
    0013 1AD0 0
    0014 1013 0
    0015 1F90 1
    0016 0063 1
    0017 1016 1
    0018 1180 0
    0019 1016 1
    001A 1D90 1
    001B 18D0 1
    001C 101B 1
    001D 0F01 1
    001E 1950 1
    001F 0FFF 0
    0020 0C01 1
    0021 018B 0
    0022 0B81 0
    0023 1AD0 0
    0024 1023 0
    0025 1B50 1
    0026 104F 1
    0027 0F04 1
    0028 0188 1
    0029 18D0 0
    002A 1029 0
    002B 0F02 1
    002C 0182 1
    002D 1304 0
    002E 1305 0
    002F 0F6E 1
    0030 0B82 1
    0031 0F00 0
    0032 0B83 0
    0033 0006 0
    0034 0B04 0
    0035 0007 0
    0036 0805 0
    0037 1584 0
    0038 1685 0
    0039 1004 1
    003A 1282 1
    003B 1083 1
    003C 1A40 1
    003D 1033 1
    003E 1F90 1
    003F 1AD0 1
    0040 103F 1
    0041 1584 1
    0042 1685 1
    0043 0590 1
    0044 18D0 1
    0045 1044 0
    0046 1950 1
    0047 103F 1
    0048 1D90 1
    0049 1AD0 1
    004A 1049 1
    004B 18D0 1
    004C 104B 1
    004D 1B50 1
    004E 102B 1
    004F 18D0 1
    0050 104F 1
    0051 1B50 1
    0052 1011 1
    0053 1053 1
    0054 018B 1
    0055 1ED1 1
    0056 1ED0 0
    0057 0F03 1
    0058 0BC1 1
    0059 0F8A 0
    005A 0BC0 0
    005B 0F56 0
    005C 0063 0
    005D 105C 0
    005E 11C0 0
    005F 105C 1
    0060 11C1 1
    0061 105C 1
    0062 1CD0 1
    0063 0F03 1
    0064 0BC1 1
    0065 0F8A 0
    0066 0BC0 0
    0067 0F56 0
    0068 0063 0
    0069 1068 0
    006A 11C0 0
    006B 1068 1
    006C 11C1 1
    006D 1068 1
    006E 1056 1
    006F 1FFF 1

 304013520: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0002 0
    07F1 0002 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1850 1
    07F9 1F54 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 027F 1
    07FF 11FD 1

 308485046: FLASH_READ_B

    ADDR DATA ?
    -----------
    0000 0070 0
    0001 0F00 0
    0002 0180 0
    0003 1FED 0
    0004 0183 0
    0005 1FEE 0
    0006 0198 0
    0007 0F80 0
    0008 0199 0
    0009 071C 0
    000A 0181 0
    000B 1FFE 0
    000C 02FF 0
    000D 1054 0
    000E 1FED 0
    000F 0981 1
    0010 1F91 1
    0011 0701 0
    0012 0380 0
    0013 1AD0 0
    0014 1013 0
    0015 1F90 1
    0016 0063 1
    0017 1012 1
    0018 1180 0
    0019 1006 0
    001A 1D90 1
    001B 1850 1
    001C 101B 1
    001D 0F00 1
    001E 1910 1
    001F 0FFF 0
    0020 0C00 1
    0021 008B 0
    0022 0B81 0
    0023 1AD0 0
    0024 1023 0
    0025 1950 1
    0026 104F 1
    0027 0F00 0
    0028 0180 1
    0029 18D0 0
    002A 1020 0
    002B 0F02 1
    002C 0080 1
    002D 1304 0
    002E 1301 0
    002F 0F6E 0
    0030 0B80 1
    0031 0F00 0
    0032 0B83 0
    0033 0006 0
    0034 0900 0
    0035 0003 0
    0036 0005 0
    0037 1584 0
    0038 1685 0
    0039 1000 0
    003A 1202 1
    003B 1081 1
    003C 1A40 1
    003D 1013 1
    003E 1F90 1
    003F 1AD0 1
    0040 103F 1
    0041 1584 1
    0042 1285 1
    0043 0590 1
    0044 1850 1
    0045 1004 0
    0046 1910 1
    0047 101F 1
    0048 1C90 1
    0049 1AD0 1
    004A 1000 1
    004B 18D0 1
    004C 1003 1
    004D 1B50 1
    004E 1023 1
    004F 1850 1
    0050 1007 1
    0051 1B50 1
    0052 1011 1
    0053 1013 1
    0054 0183 1
    0055 1ED1 1
    0056 1ED0 0
    0057 0F03 1
    0058 0BC0 1
    0059 0F8A 0
    005A 0BC0 0
    005B 0F56 0
    005C 0063 0
    005D 105C 0
    005E 10C0 0
    005F 101C 1
    0060 11C0 1
    0061 101C 1
    0062 1CD0 1
    0063 0F03 1
    0064 03C0 1
    0065 0F8A 0
    0066 0BC0 0
    0067 0F56 0
    0068 0063 0
    0069 1060 0
    006A 10C0 0
    006B 1028 1
    006C 10C1 1
    006D 1028 1
    006E 1056 1
    006F 1FFF 1

 315382652: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    0000 0070 2F00 0182 3FED
    0004 018B 3FEE 019A 2F80
    0008 019B 2F1C 0183 3FFE
    000C 2AFF 3054 3FED 0B81
    0010 1F91 2F05 0B80 1AD0
    0014 3013 1F90 0063 3016
    0018 1180 3016 1D90 18D0
    001C 301B 2F01 1950 2FFF
    0020 0C01 018B 0B81 1AD0
    0024 3023 1B50 304F 2F04
    0028 0188 18D0 3029 2F02
    002C 0182 1304 1305 2F6E
    0030 0B82 2F00 0B83 0006
    0034 0B04 0007 0805 1584
    0038 1685 1004 1282 1083
    003C 1A40 3033 1F90 1AD0
    0040 303F 1584 1685 0590
    0044 18D0 3044 1950 303F
    0048 1D90 1AD0 3049 18D0
    004C 304B 1B50 302B 18D0
    0050 304F 1B50 3011 3053
    0054 018B 1ED1 1ED0 2F03
    0058 0BC1 2F8A 0BC0 2F56
    005C 0063 305C 11C0 305C
    0060 11C1 305C 1CD0 2F03
    0064 0BC1 2F8A 0BC0 2F56
    0068 0063 3068 11C0 3068
    006C 11C1 3068 3056 3FFF


 326049413: 0000001101001010001110011010010100011100
 348308113: 0000001101001010001110011010010100011100
 373491264: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 0282 31FD


 378464965: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1850 1
    07F9 1F54 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 0282 1
    07FF 11FD 1

 383944624: FLASH_READ_B

    ADDR DATA ?
    -----------
    07E0 1FFF 0
    07E1 1FFF 0
    07E2 1FFF 1
    07E3 1FFF 1
    07E4 1FFF 1
    07E5 1FFF 1
    07E6 1FFF 1
    07E7 1FFF 1
    07E8 1FFF 1
    07E9 1FFF 1
    07EA 1FFF 1
    07EB 1FFF 1
    07EC 1FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0002 0
    07F1 0002 1
    07F2 1FFF 0
    07F3 1FFF 0
    07F4 1FFF 1
    07F5 1FFF 1
    07F6 1FFF 1
    07F7 1FFF 1
    07F8 1850 1
    07F9 1F54 1
    07FA 1FFF 1
    07FB 1FFF 1
    07FC 1FFF 1
    07FD 1FFF 1
    07FE 0202 1
    07FF 11FD 1

 388416397: FLASH_WRITE_B

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 0282 31FD




And when sampling on the falling edge:
Code: [Select]
116050423: FLASH_READ_A
    No data (dummy read)

 121460335: FLASH_READ_A

    ADDR DATA ?
    -----------
    07EF 1FFE 0
    07F0 0025 0
    07F1 0025 1

 125171918: ??? (1010010110100101101001011010001100011010101000010)

 132819443: ??? (1010010110100101101001011010011001111010101000010)

 189654150: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07F0 0026 3FFF 3FFF 3FFF


 194375883: FLASH_READ_A

    ADDR DATA ?
    -----------
    07F0 0026 0

 198033633: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07F0 3FFF 0026 3FFF 3FFF


 202755366: FLASH_READ_A

    ADDR DATA ?
    -----------
    07F1 0026 1

 206415178: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 3FFF 1
    07F9 3FFF 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 3FFF 1
    07FF 3FFF 1

 210877122: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 3FFF 1
    07F9 3FFF 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 3FFF 1
    07FF 3FFF 1

 216360794: FLASH_READ_A

    ADDR DATA ?
    -----------
    0000 3FFF 0
    0001 3FFF 0
    0002 3FFF 1
    0003 3FFF 1
    0004 3FFF 1
    0005 3FFF 1
    0006 3FFF 1
    0007 3FFF 1
    0008 3FFF 1
    0009 3FFF 1
    000A 3FFF 1
    000B 3FFF 1
    000C 3FFF 1
    000D 3FFF 1
    000E 3FFF 1
    000F 3FFF 1
    0010 3FFF 1
    0011 3FFF 1
    0012 3FFF 1
    0013 3FFF 1
    0014 3FFF 1
    0015 3FFF 1
    0016 3FFF 1
    0017 3FFF 1
    0018 3FFF 1
    0019 3FFF 1
    001A 3FFF 1
    001B 3FFF 1
    001C 3FFF 1
    001D 3FFF 1
    001E 3FFF 1
    001F 3FFF 1
    0020 3FFF 1
    0021 3FFF 1
    0022 3FFF 1
    0023 3FFF 1
    0024 3FFF 1
    0025 3FFF 1
    0026 3FFF 1
    0027 3FFF 1
    0028 3FFF 1
    0029 3FFF 1
    002A 3FFF 1
    002B 3FFF 1
    002C 3FFF 1
    002D 3FFF 1
    002E 3FFF 1
    002F 3FFF 1
    0030 3FFF 1
    0031 3FFF 1
    0032 3FFF 1
    0033 3FFF 1
    0034 3FFF 1
    0035 3FFF 1
    0036 3FFF 1
    0037 3FFF 1
    0038 3FFF 1
    0039 3FFF 1
    003A 3FFF 1
    003B 3FFF 1
    003C 3FFF 1
    003D 3FFF 1
    003E 3FFF 1
    003F 3FFF 1
    0040 3FFF 1
    0041 3FFF 1
    0042 3FFF 1
    0043 3FFF 1
    0044 3FFF 1
    0045 3FFF 1
    0046 3FFF 1
    0047 3FFF 1
    0048 3FFF 1
    0049 3FFF 1
    004A 3FFF 1
    004B 3FFF 1
    004C 3FFF 1
    004D 3FFF 1
    004E 3FFF 1
    004F 3FFF 1
    0050 3FFF 1
    0051 3FFF 1
    0052 3FFF 1
    0053 3FFF 1
    0054 3FFF 1
    0055 3FFF 1
    0056 3FFF 1
    0057 3FFF 1
    0058 3FFF 1
    0059 3FFF 1
    005A 3FFF 1
    005B 3FFF 1
    005C 3FFF 1
    005D 3FFF 1
    005E 3FFF 1
    005F 3FFF 1
    0060 3FFF 1
    0061 3FFF 1
    0062 3FFF 1
    0063 3FFF 1
    0064 3FFF 1
    0065 3FFF 1
    0066 3FFF 1
    0067 3FFF 1
    0068 3FFF 1
    0069 3FFF 1
    006A 3FFF 1
    006B 3FFF 1
    006C 3FFF 1
    006D 3FFF 1
    006E 3FFF 1
    006F 3FFF 1
    0070 3FFF 1
    0071 3FFF 1
    0072 3FFF 1
    0073 3FFF 1
    0074 3FFF 1
    0075 3FFF 1
    0076 3FFF 1
    0077 3FFF 1
    0078 3FFF 1
    0079 3FFF 1
    007A 3FFF 1
    007B 3FFF 1
    007C 3FFF 1
    007D 3FFF 1
    007E 3FFF 1
    007F 3FFF 1
    0080 3FFF 1
    0081 3FFF 1
    0082 3FFF 1
    0083 3FFF 1
    0084 3FFF 1
    0085 3FFF 1
    0086 3FFF 1
    0087 3FFF 1
    0088 3FFF 1
    0089 3FFF 1
    008A 3FFF 1
    008B 3FFF 1
    008C 3FFF 1
    008D 3FFF 1
    008E 3FFF 1
    008F 3FFF 1
    0090 3FFF 1
    0091 3FFF 1
    0092 3FFF 1
    0093 3FFF 1
    0094 3FFF 1
    0095 3FFF 1
    0096 3FFF 1
    0097 3FFF 1
    0098 3FFF 1
    0099 3FFF 1
    009A 3FFF 1
    009B 3FFF 1
    009C 3FFF 1
    009D 3FFF 1
    009E 3FFF 1
    009F 3FFF 1
    00A0 3FFF 1
    00A1 3FFF 1
    00A2 3FFF 1
    00A3 3FFF 1
    00A4 3FFF 1
    00A5 3FFF 1
    00A6 3FFF 1
    00A7 3FFF 1
    00A8 3FFF 1
    00A9 3FFF 1
    00AA 3FFF 1
    00AB 3FFF 1
    00AC 3FFF 1
    00AD 3FFF 1
    00AE 3FFF 1
    00AF 3FFF 1
    00B0 3FFF 1
    00B1 3FFF 1
    00B2 3FFF 1
    00B3 3FFF 1
    00B4 3FFF 1
    00B5 3FFF 1
    00B6 3FFF 1
    00B7 3FFF 1
    00B8 3FFF 1
    00B9 3FFF 1
    00BA 3FFF 1
    00BB 3FFF 1
    00BC 3FFF 1
    00BD 3FFF 1
    00BE 3FFF 1
    00BF 3FFF 1
    00C0 3FFF 1
    00C1 3FFF 1
    00C2 3FFF 1
    00C3 3FFF 1
    00C4 3FFF 1
    00C5 3FFF 1
    00C6 3FFF 1
    00C7 3FFF 1
    00C8 3FFF 1
    00C9 3FFF 1
    00CA 3FFF 1
    00CB 3FFF 1
    00CC 3FFF 1
    00CD 3FFF 1
    00CE 3FFF 1
    00CF 3FFF 1
    00D0 3FFF 1
    00D1 3FFF 1
    00D2 3FFF 1
    00D3 3FFF 1
    00D4 3FFF 1
    00D5 3FFF 1
    00D6 3FFF 1
    00D7 3FFF 1
    00D8 3FFF 1
    00D9 3FFF 1
    00DA 3FFF 1
    00DB 3FFF 1
    00DC 3FFF 1
    00DD 3FFF 1
    00DE 3FFF 1
    00DF 3FFF 1
    00E0 3FFF 1
    00E1 3FFF 1
    00E2 3FFF 1
    00E3 3FFF 1
    00E4 3FFF 1
    00E5 3FFF 1
    00E6 3FFF 1
    00E7 3FFF 1
    00E8 3FFF 1
    00E9 3FFF 1
    00EA 3FFF 1
    00EB 3FFF 1
    00EC 3FFF 1
    00ED 3FFF 1
    00EE 3FFF 1
    00EF 3FFF 1
    00F0 3FFF 1
    00F1 3FFF 1
    00F2 3FFF 1
    00F3 3FFF 1
    00F4 3FFF 1
    00F5 3FFF 1
    00F6 3FFF 1
    00F7 3FFF 1
    00F8 3FFF 1
    00F9 3FFF 1
    00FA 3FFF 1
    00FB 3FFF 1
    00FC 3FFF 1
    00FD 3FFF 1
    00FE 3FFF 1
    00FF 3FFF 1
    0100 3FFF 1
    0101 3FFF 1
    0102 3FFF 1
    0103 3FFF 1
    0104 3FFF 1
    0105 3FFF 1
    0106 3FFF 1
    0107 3FFF 1
    0108 3FFF 1
    0109 3FFF 1
    010A 3FFF 1
    010B 3FFF 1
    010C 3FFF 1
    010D 3FFF 1
    010E 3FFF 1
    010F 3FFF 1
    0110 3FFF 1
    0111 3FFF 1
    0112 3FFF 1
    0113 3FFF 1
    0114 3FFF 1
    0115 3FFF 1
    0116 3FFF 1
    0117 3FFF 1
    0118 3FFF 1
    0119 3FFF 1
    011A 3FFF 1
    011B 3FFF 1
    011C 3FFF 1
    011D 3FFF 1
    011E 3FFF 1
    011F 3FFF 1
    0120 3FFF 1
    0121 3FFF 1
    0122 3FFF 1
    0123 3FFF 1
    0124 3FFF 1
    0125 3FFF 1
    0126 3FFF 1
    0127 3FFF 1
    0128 3FFF 1
    0129 3FFF 1
    012A 3FFF 1
    012B 3FFF 1
    012C 3FFF 1
    012D 3FFF 1
    012E 3FFF 1
    012F 3FFF 1
    0130 3FFF 1
    0131 3FFF 1
    0132 3FFF 1
    0133 3FFF 1
    0134 3FFF 1
    0135 3FFF 1
    0136 3FFF 1
    0137 3FFF 1
    0138 3FFF 1
    0139 3FFF 1
    013A 3FFF 1
    013B 3FFF 1
    013C 3FFF 1
    013D 3FFF 1
    013E 3FFF 1
    013F 3FFF 1
    0140 3FFF 1
    0141 3FFF 1
    0142 3FFF 1
    0143 3FFF 1
    0144 3FFF 1
    0145 3FFF 1
    0146 3FFF 1
    0147 3FFF 1
    0148 3FFF 1
    0149 3FFF 1
    014A 3FFF 1
    014B 3FFF 1
    014C 3FFF 1
    014D 3FFF 1
    014E 3FFF 1
    014F 3FFF 1
    0150 3FFF 1
    0151 3FFF 1
    0152 3FFF 1
    0153 3FFF 1
    0154 3FFF 1
    0155 3FFF 1
    0156 3FFF 1
    0157 3FFF 1
    0158 3FFF 1
    0159 3FFF 1
    015A 3FFF 1
    015B 3FFF 1
    015C 3FFF 1
    015D 3FFF 1
    015E 3FFF 1
    015F 3FFF 1
    0160 3FFF 1
    0161 3FFF 1
    0162 3FFF 1
    0163 3FFF 1
    0164 3FFF 1
    0165 3FFF 1
    0166 3FFF 1
    0167 3FFF 1
    0168 3FFF 1
    0169 3FFF 1
    016A 3FFF 1
    016B 3FFF 1
    016C 3FFF 1
    016D 3FFF 1
    016E 3FFF 1
    016F 3FFF 1
    0170 3FFF 1
    0171 3FFF 1
    0172 3FFF 1
    0173 3FFF 1
    0174 3FFF 1
    0175 3FFF 1
    0176 3FFF 1
    0177 3FFF 1
    0178 3FFF 1
    0179 3FFF 1
    017A 3FFF 1
    017B 3FFF 1
    017C 3FFF 1
    017D 3FFF 1
    017E 3FFF 1
    017F 3FFF 1
    [cut to keep under 50k chars - all is 3FFF]
    07C0 3FFF 1
    07C1 3FFF 1
    07C2 3FFF 1
    07C3 3FFF 1
    07C4 3FFF 1
    07C5 3FFF 1
    07C6 3FFF 1
    07C7 3FFF 1
    07C8 3FFF 1
    07C9 3FFF 1
    07CA 3FFF 1
    07CB 3FFF 1
    07CC 3FFF 1
    07CD 3FFF 1
    07CE 3FFF 1
    07CF 3FFF 1
    07D0 3FFF 1
    07D1 3FFF 1
    07D2 3FFF 1
    07D3 3FFF 1
    07D4 3FFF 1
    07D5 3FFF 1
    07D6 3FFF 1
    07D7 3FFF 1
    07D8 3FFF 1
    07D9 3FFF 1
    07DA 3FFF 1
    07DB 3FFF 1
    07DC 3FFF 1
    07DD 3FFF 1
    07DE 3FFF 1
    07DF 3FFF 1

 274899188: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    0000 0070 2F00 0182 3FED
    0004 018B 3FEE 019A 2F80
    0008 019B 2F1C 0183 3FFE
    000C 2AFF 3054 3FED 0B81
    0010 1F91 2F05 0B80 1AD0
    0014 3013 1F90 0063 3016
    0018 1180 3016 1D90 18D0
    001C 301B 2F01 1950 2FFF
    0020 0C01 018B 0B81 1AD0
    0024 3023 1B50 304F 2F04
    0028 0188 18D0 3029 2F02
    002C 0182 1304 1305 2F6E
    0030 0B82 2F00 0B83 0006
    0034 0B04 0007 0805 1584
    0038 1685 1004 1282 1083
    003C 1A40 3033 1F90 1AD0
    0040 303F 1584 1685 0590
    0044 18D0 3044 1950 303F
    0048 1D90 1AD0 3049 18D0
    004C 304B 1B50 302B 18D0
    0050 304F 1B50 3011 3053
    0054 018B 1ED1 1ED0 2F03
    0058 0BC1 2F8A 0BC0 2F56
    005C 0063 305C 11C0 305C
    0060 11C1 305C 1CD0 2F03
    0064 0BC1 2F8A 0BC0 2F56
    0068 0063 3068 11C0 3068
    006C 11C1 3068 3056 3FFF


 282886688: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 02FF 31FD


 290648239: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 1850 1
    07F9 3F54 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 02FF 1
    07FF 31FD 1

 296126144: FLASH_READ_A

    ADDR DATA ?
    -----------
    0000 0070 0
    0001 2F00 0
    0002 0182 0
    0003 3FED 0
    0004 018B 0
    0005 3FEE 1
    0006 019A 0
    0007 2F80 1
    0008 019B 0
    0009 2F1C 0
    000A 0183 0
    000B 3FFE 0
    000C 2AFF 0
    000D 3054 1
    000E 3FED 0
    000F 0B81 1
    0010 1F91 1
    0011 2F05 0
    0012 0B80 1
    0013 1AD0 0
    0014 3013 0
    0015 1F90 1
    0016 0063 1
    0017 3016 1
    0018 1180 0
    0019 3016 1
    001A 1D90 1
    001B 18D0 1
    001C 301B 1
    001D 2F01 1
    001E 1950 1
    001F 2FFF 0
    0020 0C01 1
    0021 018B 0
    0022 0B81 0
    0023 1AD0 0
    0024 3023 0
    0025 1B50 1
    0026 304F 1
    0027 2F04 1
    0028 0188 1
    0029 18D0 0
    002A 3029 0
    002B 2F02 1
    002C 0182 1
    002D 1304 0
    002E 1305 0
    002F 2F6E 1
    0030 0B82 1
    0031 2F00 0
    0032 0B83 0
    0033 0006 0
    0034 0B04 0
    0035 0007 0
    0036 0805 0
    0037 1584 0
    0038 1685 0
    0039 1004 1
    003A 1282 1
    003B 1083 1
    003C 1A40 1
    003D 3033 1
    003E 1F90 1
    003F 1AD0 1
    0040 303F 1
    0041 1584 1
    0042 1685 1
    0043 0590 1
    0044 18D0 1
    0045 3044 0
    0046 1950 1
    0047 303F 1
    0048 1D90 1
    0049 1AD0 1
    004A 3049 1
    004B 18D0 1
    004C 304B 1
    004D 1B50 1
    004E 302B 1
    004F 18D0 1
    0050 304F 1
    0051 1B50 1
    0052 3011 1
    0053 3053 1
    0054 018B 1
    0055 1ED1 1
    0056 1ED0 0
    0057 2F03 1
    0058 0BC1 1
    0059 2F8A 0
    005A 0BC0 0
    005B 2F56 0
    005C 0063 0
    005D 305C 0
    005E 11C0 0
    005F 305C 1
    0060 11C1 1
    0061 305C 1
    0062 1CD0 1
    0063 2F03 1
    0064 0BC1 1
    0065 2F8A 0
    0066 0BC0 0
    0067 2F56 0
    0068 0063 0
    0069 3068 0
    006A 11C0 0
    006B 3068 1
    006C 11C1 1
    006D 3068 1
    006E 3056 1
    006F 3FFF 1

 304013692: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 1850 1
    07F9 3F54 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 02FF 1
    07FF 31FD 1

 308485218: FLASH_READ_A

    ADDR DATA ?
    -----------
    0000 0070 0
    0001 2F00 0
    0002 0182 0
    0003 3FED 0
    0004 018B 0
    0005 3FEE 0
    0006 019A 0
    0007 2F80 0
    0008 019B 0
    0009 2F1C 0
    000A 0183 0
    000B 3FFE 0
    000C 2AFF 0
    000D 3054 0
    000E 3FED 0
    000F 0B81 1
    0010 1F91 1
    0011 2F05 0
    0012 0B80 0
    0013 1AD0 0
    0014 3013 0
    0015 1F90 1
    0016 0063 1
    0017 3016 1
    0018 1180 0
    0019 3016 0
    001A 1D90 1
    001B 18D0 1
    001C 301B 1
    001D 2F01 1
    001E 1950 1
    001F 2FFF 0
    0020 0C01 1
    0021 018B 0
    0022 0B81 0
    0023 1AD0 0
    0024 3023 0
    0025 1B50 1
    0026 304F 1
    0027 2F04 0
    0028 0188 1
    0029 18D0 0
    002A 3029 0
    002B 2F02 1
    002C 0182 1
    002D 1304 0
    002E 1305 0
    002F 2F6E 0
    0030 0B82 1
    0031 2F00 0
    0032 0B83 0
    0033 0006 0
    0034 0B04 0
    0035 0007 0
    0036 0805 0
    0037 1584 0
    0038 1685 0
    0039 1004 0
    003A 1282 1
    003B 1083 1
    003C 1A40 1
    003D 3033 1
    003E 1F90 1
    003F 1AD0 1
    0040 303F 1
    0041 1584 1
    0042 1685 1
    0043 0590 1
    0044 18D0 1
    0045 3044 0
    0046 1950 1
    0047 303F 1
    0048 1D90 1
    0049 1AD0 1
    004A 3049 1
    004B 18D0 1
    004C 304B 1
    004D 1B50 1
    004E 302B 1
    004F 18D0 1
    0050 304F 1
    0051 1B50 1
    0052 3011 1
    0053 3053 1
    0054 018B 1
    0055 1ED1 1
    0056 1ED0 0
    0057 2F03 1
    0058 0BC1 1
    0059 2F8A 0
    005A 0BC0 0
    005B 2F56 0
    005C 0063 0
    005D 305C 0
    005E 11C0 0
    005F 305C 1
    0060 11C1 1
    0061 305C 1
    0062 1CD0 1
    0063 2F03 1
    0064 0BC1 1
    0065 2F8A 0
    0066 0BC0 0
    0067 2F56 0
    0068 0063 0
    0069 3068 0
    006A 11C0 0
    006B 3068 1
    006C 11C1 1
    006D 3068 1
    006E 3056 1
    006F 3FFF 1

 315382824: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    0000 0070 2F00 0182 3FED
    0004 018B 3FEE 019A 2F80
    0008 019B 2F1C 0183 3FFE
    000C 2AFF 3054 3FED 0B81
    0010 1F91 2F05 0B80 1AD0
    0014 3013 1F90 0063 3016
    0018 1180 3016 1D90 18D0
    001C 301B 2F01 1950 2FFF
    0020 0C01 018B 0B81 1AD0
    0024 3023 1B50 304F 2F04
    0028 0188 18D0 3029 2F02
    002C 0182 1304 1305 2F6E
    0030 0B82 2F00 0B83 0006
    0034 0B04 0007 0805 1584
    0038 1685 1004 1282 1083
    003C 1A40 3033 1F90 1AD0
    0040 303F 1584 1685 0590
    0044 18D0 3044 1950 303F
    0048 1D90 1AD0 3049 18D0
    004C 304B 1B50 302B 18D0
    0050 304F 1B50 3011 3053
    0054 018B 1ED1 1ED0 2F03
    0058 0BC1 2F8A 0BC0 2F56
    005C 0063 305C 11C0 305C
    0060 11C1 305C 1CD0 2F03
    0064 0BC1 2F8A 0BC0 2F56
    0068 0063 3068 11C0 3068
    006C 11C1 3068 3056 3FFF


 337347740: 0000001010010100011101010100101000111010
 359606267: 0000001010010100011101010100101000111010
 373491436: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 0282 31FD


 378465137: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 1850 1
    07F9 3F54 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 0282 1
    07FF 31FD 1

 383944796: FLASH_READ_A

    ADDR DATA ?
    -----------
    07E0 3FFF 0
    07E1 3FFF 0
    07E2 3FFF 1
    07E3 3FFF 1
    07E4 3FFF 1
    07E5 3FFF 1
    07E6 3FFF 1
    07E7 3FFF 1
    07E8 3FFF 1
    07E9 3FFF 1
    07EA 3FFF 1
    07EB 3FFF 1
    07EC 3FFF 1
    07ED 0281 1
    07EE 027A 1
    07EF 1FFE 0
    07F0 0026 0
    07F1 0026 1
    07F2 3FFF 0
    07F3 3FFF 0
    07F4 3FFF 1
    07F5 3FFF 1
    07F6 3FFF 1
    07F7 3FFF 1
    07F8 1850 1
    07F9 3F54 1
    07FA 3FFF 1
    07FB 3FFF 1
    07FC 3FFF 1
    07FD 3FFF 1
    07FE 0282 1
    07FF 31FD 1

 388416569: FLASH_WRITE_A

    ADDR -W1- -W2- -W3- -W4-
    ------------------------
    07EC 3FFF 0281 027A 1FFE
    07F0 0026 0026 3FFF 3FFF
    07F8 1850 3F54 3FFF 3FFF
    07FC 3FFF 3FFF 0282 31FD




We can now be sure that:

EDIT: There's a repo I've made for the tiny Python scripts I'm using, since uploading them manually here is annoying: https://github.com/socram8888/pdkscope
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 31, 2018, 07:15:51 am
Thanks for the new capture.

One odd thing I noticed is that the clock duty cycle changes during the data transmissions (and commands) maybe thats indicative of a handover to the micro being programmed: active output -> pull-up on the programmer side and pulldown on the micro side.

Then the trailing AA1 could be an acknowledge by the micro during commands
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 31, 2018, 07:18:53 am
In this sequence of the verify it looks like the programmer supplies the adress and then the micro responds with the data.

The micro probably samples on rising edges, the programmer on falling.

Format changes as well, 8bitish for the commands, 14 bitish for the data/adresses -> probably different for different core sizes. (PICs have padding to make it all nice and 16bitish ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 31, 2018, 09:51:59 am
Whats a bit weird is that it seems to write during verify also.

I assume that its writing because the clocks after command 0x70 and data are slower than usual (8 clock cycles total).
Also while its reading in address/data fashion, it writes 4 words at a time (5*14=70 bits, one address first I assume)

Maybe its re-writing and re-reading bits that didnt match?

Towards the end there seem to be two runs of the calibration program followed by writes to the calibration bytes.

The last command is also a write, that isnt read back/verified. Maybe a usage counter? Why?

Vpp -> Vdd : 200 us
Vdd -> Data : 1000 us
larger pauses to stabilize voltages?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 31, 2018, 10:07:59 am
There was a slightly problem while I was exporting the TXT file for processing, apparently the LAP-C program didn't like exporting a 20GB file and crashed before finishing  ;D

So I'm not sure if the file contains all the commands and all the messages. The program doesn't display what percentage of the file it has processed, so I'm not sure how much data was still remaining to be exported.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 31, 2018, 10:21:54 am
There was a slightly problem while I was exporting the TXT file for processing, apparently the LAP-C program didn't like exporting a 20GB file and crashed before finishing  ;D

So I'm not sure if the file contains all the commands and all the messages. The program doesn't display what percentage of the file it has processed, so I'm not sure how much data was still remaining to be exported.

You dont need to export everything, just the command sequences would be fine. At the beginning and end theres blank checking.
There are two phases where data is read and there are shorter phases in between where I think data is beeing re-writen.
Maybe you can just export shorter parts.

You have to set bars and export from bar to bar. But you can only use A and B bar Why?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 31, 2018, 11:03:33 am
I've just checked by opening the TXT and looking at the timestamps it actually exported everything, from -4864 to 500936754.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 31, 2018, 12:38:19 pm
Great findings from all of you.

I think it's time to test some of the observations. I will start with the VERIFY (READ).

I will assume that VDD/VPP = 3.3V will be ok for this. Then I just can connect the input/output of the host MCU to padauk IC directly.

After looking at the different bit counts for input / output transmissions which can not be mapped to 8 bit I think using the hardware SPI of host MCU will not work out well.

This means I will try to bit bang the protocol with a tight loop (might be hard when capturing input from IC assuming 1MHz clock).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on December 31, 2018, 12:53:43 pm
I will assume that VDD/VPP = 3.3V will be ok for this. Then I just can connect the input/output of the host MCU to padauk IC directly.

I'm not sure this will work.
The sequence must probably be observed:
Apply Vpp (5.6V) before Vdd (2.6V) (thats the same as with PICs)    -> select programming mode, command phase
Send command
Change Vdd to 4.3V to read data   -> data phase

I think theres a voltage dependent state machine at work that tells the micro what to do.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 31, 2018, 01:09:01 pm
Maybe it does, or maybe it just relies on the order rather than actual voltages. I think it's worth looking before proceeding with designing the programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 31, 2018, 05:06:10 pm
First test result:

VPP 3.3V seems NOT to work. IC starts exactly same as when VPP is not applied (52.40ms till blink out starts on PA.3)

Need to add transistor now to toggle 5V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 31, 2018, 06:03:21 pm
First test result:

VPP 3.3V seems NOT to work. IC starts exactly same as when VPP is not applied (52.40ms till blink out starts on PA.3)

Need to add transistor now to toggle 5V.
I'd try 3.3V on VDD rather than VPP.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 03:25:17 pm
I did some experiments.

Everything up to 5.5V on VPP (PA.5) is ignored (this is maximum rating in IC data sheet for VDD and pins) and IC starts up normally.

As soon >5.6V (tested up to 12V) is present on VPP (PA.5) the startup of the IC is different (I guess programing/command mode).

Need to hook up logic analyzer to bread board now.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 06:32:44 pm
FIRST BIG SUCCESS...

After some try and error I completed Level1  ^-^ ^-^ : CLOCK is ALWAYS sent from WRITER.

- a command is sent with preamble 0xA5A5A5A followed by 8 bit COMMAND
- after last bit from command was sent DATA switches directions
- IC sends back 0xAA and 4 bit status (maybe something like this: b0001 = ok, b0000 = error), clock must be supplied by WRITER

This only works with VPP > 5.5 V.

JS

EDIT: 3.3V was used for VDD.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 01, 2019, 07:09:48 pm
Great job! The IC seems to be sampling the data pin on falling edge, then, is that right?  While it seems the incoming data must be sampled on the rising edge.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 07:36:17 pm
Great job! The IC seems to be sampling the data pin on falling edge, then, is that right?  While it seems the incoming data must be sampled on the rising edge.

Not there yet ... in command mode it looks like I can sample either on rising or on falling edge.

Could you describe the READ command (0x60) in detail?

>A5A5A5A60
<AA1

>? ? ?
<? ? ?
...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 01, 2019, 08:20:08 pm
>A5A5A5A60
<AA1

>? ? ?
<? ? ?

AFAICT the programmer supplies the address of the location it wants to read (looking at the dutycycle of the clock) see the picture in my post December 31, 2018, 08:51:59 pm.
Starting with 0 and counting up. 14 bit address from the programmer, then 14 bits of data are returned by the micro.
I guess the clock is supplied by the programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 01, 2019, 08:24:53 pm
Maybe the vdd voltage has to be changed as well. From 2.6V to 4.3V.
Might be important for the micro to distinguish between command and data modes.
However might not be as sensitive to the actual voltage as I thought, so maybe 2.5V and 5V is fine.
Or no change at all ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 01, 2019, 08:35:59 pm
Not there yet ... in command mode it looks like I can sample either on rising or on falling edge.

Could you describe the READ command (0x60) in detail?
Sure.
Code: [Select]
Enter read mode:
>A5A5A5A61 (36 bits)
<1010 1010 0001 0 (13 bits)

Voltage is on VDD now raised to 4.3V

Read word:
>address (13 bits)
<word (14 bits)
>unknown, seemingly always 1 (1 bit)
Note command seems to be 61 instead of 60, or at least that what I got from the 200 MHz dump, and from previous using the "sticky" (ie one if it's high on either falling or rising) approach.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 01, 2019, 08:46:36 pm
Maybe the last bit is just an ACK?
If you supply an adress outside of the chips memory range > 2048 for the PFS154 maybe it returns 0?

Maybe thats the stop condition for a read? Edit: Nope.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 01, 2019, 09:02:47 pm
Write command format, in case you want to try it:
Code: [Select]
>A5A5A5A71 (36 bits)
<1010 1010 0001 0 (13 bits)

VPP is raised to 8.3V

<word1 (14 bits)
<word2 (14 bits)
<word3 (14 bits)
<word4 (14 bits)
<address (13 bits)
<000000000 (padding? not sure about the direction of this one - 9 bits)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 01, 2019, 09:49:35 pm
<000000000 (padding? not sure about the direction of this one - 9 bits)

Thats probably just something to get the micro to program the locations after the data has been supplied.

There's also a one right before that that appears on the data line but is not accompanied by a clockcycle. Dont know whats that for or if its even important.

Also shouldn't it be >word above?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 10:14:21 pm
Level 2 done... complete readout.

Attached the logic analyzer capture from the readout. I decreased some stupid delays and did not make the song and dance at the beginning. Just send command 0x60 and then read data.

Summary:
VPP: 5.6V
VDD: 3.3V
>0xA5A5A5A
>0x60
<0xAA1
>0x0000  (14 bit addr)
<0x0070  (14 bit data)
>0x0001  (14 bit addr)
<0x2F00  (14 bit data)
...
>0x07FF  (14 bit addr)
<0x31FD (14 bit data)
VDD: 0V
VPP: 0V

 8) 8) 8) 8) 8)

JS


EDIT: I'm tempted to set security bit.... and try again ;-)

EDIT2: It was not working when using 13 bit address... not sure why. Maybe clock style is wrong or pullup/down or ... is needed?

EDIT3: Reading from address 0x800 ... returns same as 0x000 ... (so address just wraps around)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 10:18:10 pm
Write command format, in case you want to try it:
Code: [Select]
>A5A5A5A71 (36 bits)
<1010 1010 0001 0 (13 bits)

VPP is raised to 8.3V

<word1 (14 bits)
<word2 (14 bits)
<word3 (14 bits)
<word4 (14 bits)
<address (13 bits)
<000000000 (padding? not sure about the direction of this one - 9 bits)

This is next I will try... (tomorrow maybe).

> VPP is raised to 8.3V

What I found out... READ is also working with VPP 8.3V and VPP 12.0V  so maybe just 12V VPP is needed :-) ?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 01, 2019, 10:27:02 pm
Write command format, in case you want to try it:
Code: [Select]
>A5A5A5A71 (36 bits)
<1010 1010 0001 0 (13 bits)

VPP is raised to 8.3V

<word1 (14 bits)
<word2 (14 bits)
<word3 (14 bits)
<word4 (14 bits)
<address (13 bits)
<000000000 (padding? not sure about the direction of this one - 9 bits)

This is next I will try... (tomorrow maybe).

> VPP is raised to 8.3V

What I found out... READ is also working with VPP 8.3V and VPP 12.0V  so maybe just 12V VPP is needed :-) ?

JS

That would also simplify voltage regulation significantly.
Just double (triple) Vdd and apply to Vpp. (Does it really need to be 8.3V ???)
That can be done with a charge pump.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 01, 2019, 10:29:46 pm
Could you please try also with 0x61? I wonder why I'm getting that if it's 0x60.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2019, 10:39:37 pm
Could you please try also with 0x61? I wonder why I'm getting that if it's 0x60.

OK, tested 0x60, 0x61, 0x62, ... 0x6F ... all same result: VALID READ  :)

=> seems command is just 0x6  and then 4 dummy clocks are used before switching mode (the 4 clocks are really needed, I thought maybe preamble 28 bit + 4 bit command = nice 32 bit... but nope)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 01, 2019, 11:16:18 pm
Could you please try also with 0x61? I wonder why I'm getting that if it's 0x60.

OK, tested 0x60, 0x61, 0x62, ... 0x6F ... all same result: VALID READ  :)

=> seems command is just 0x6  and then 4 dummy clocks are used before switching mode (the 4 clocks are really needed, I thought maybe preamble 28 bit + 4 bit command = nice 32 bit... but nope)

JS
That seems correct. It looks like the writer itself is using 0x67 at some point for reading in place of 0x61 and 0x60.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 02, 2019, 07:31:03 pm
FIRST BIG SUCCESS...

After some try and error I completed Level1  ^-^ ^-^ : CLOCK is ALWAYS sent from WRITER.

- a command is sent with preamble 0xA5A5A5A followed by 8 bit COMMAND
- after last bit from command was sent DATA switches directions
- IC sends back 0xAA and 4 bit status (maybe something like this: b0001 = ok, b0000 = error), clock must be supplied by WRITER

This only works with VPP > 5.5 V.

JS

EDIT: 3.3V was used for VDD.


I tried to replicate your experiment with the 0x60 command (minus powercycling I just switch it on), but I only have blank chips.
They dont respond at all.

Could you try with a blank chip?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 02, 2019, 08:00:36 pm
I tried to replicate your experiment with the 0x60 command (minus powercycling I just switch it on), but I only have blank chips.
They dont respond at all.

Could you try with a blank chip?

Which IC do you try to use?
I use PFS154-S16 (erasable flash, 1000 write cycles)

I use the following sequence (I tested with 200kHz up to almost 2MHz for CLK pulses, all working):

- enable VPP 6.0V (I use external power supply for VPP and switch it on using a transistor)
- wait 100µs
- enable VDD 3.3V (driven from STM32 GPIO output pin directly)
- wait 500µs
- switch DAT to output
- send preamble + command bit by bit (28 bit + 8 bit): 0xA5A5A5A60
    bit send loop:
   * set current bit on DAT (MSB first)
   * CLK high
     * optional wait 1µs
   * CLK low
     * optional wait 1µs
- switch DAT to input
- receive ACK (12 bit):
    bit receive loop:
    * CLK high
    * read DAT bit (MSB)
      * optional wait 1µs
    * CLK low
      * optional wait 1µs
- check that ACK is 0xAA1

- 1 extra clock
   * CLK high
     * optional wait 1µs
   * CLK low
     * optional wait 1µs
- switch DAT to output

- send address (13 bit)
- switch DAT to input
- recv data (14 bit)
- 1 extra clock
   * CLK high
     * optional wait 1µs
   * CLK low
     * optional wait 1µs
- switch DAT to output

...

- send address (13 bit)
- switch DAT to input
- recv data (14 bit)
- 1 extra clock
   * CLK high
     * optional wait 1µs
   * CLK low
     * optional wait 1µs
- switch DAT to output

- wait 100µs
- disable VDD
- wait 20µs
- disable VPP

----------------

I think the sequence "VPP on, wait 100µs, VDD on, wait 500µs, send command" is essential.
Also if you make a mistake like sending a wrong preamble or bad command the IC will exit special mode and just start normal execution.

I will try to read an empty IC later.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 02, 2019, 08:24:16 pm
I use an arduino (clone).
The code I use is a bit of a mess right now because I hardcoded the command.
My futile attempt to remove errors ;)
However it should be almost identical to the code you have.

So powercycling timing seems to be important.

Code: [Select]
void PADAUK_write_bit (unsigned char b) {
  digitalWrite(PA6_data, b);
  delayMicroseconds(1);
  digitalWrite(PA3_clk, 1);
  delayMicroseconds(1);
  digitalWrite(PA3_clk, 0);
  delayMicroseconds(1); 
}

unsigned char PADAUK_read_bit () {
  digitalWrite(PA3_clk, 1);
  delayMicroseconds(1);
  unsigned char b = digitalRead(PA6_data);
  digitalWrite(PA3_clk, 0);
  delayMicroseconds(1); 
  return b;
}

void PADAUK_command(unsigned char cmd) {
//A
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
//5
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
//A
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
//5
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
//A
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
//5
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
//A
PADAUK_write_bit(1);
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
//6
PADAUK_write_bit(0);
PADAUK_write_bit(1);
PADAUK_write_bit(1);
PADAUK_write_bit(0);
//0
PADAUK_write_bit(0);
PADAUK_write_bit(0);
PADAUK_write_bit(0);
PADAUK_write_bit(0);

pinMode(PA6_data, INPUT_PULLUP);
delayMicroseconds(1);

PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();

PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();

PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();
PADAUK_read_bit();

pinMode(PA6_data, OUTPUT);
digitalWrite(PA6_data, 0);
}

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 02, 2019, 08:25:19 pm
The output waveform looks identical to your capture otherwise.

Vdd is 5V, Vpp is 7.8 right now but I have tried several values from 5.6 to 12 V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 02, 2019, 10:17:28 pm
Level 3 done  8) :

I just got ERASE working.

I had to insert one small extra CLK directly after command, so ERASE sequence was like this (maybe can be stripped down):
- enable VPP 8.3V
- wait 100µs
- enable VDD 3.3V
- wait 500 µs
- send preamble+command (28 bit + 8 bit): 0xA5A5A5A30
- receive ack (12 bit)
- CLK_UP
- CLK_DOWN
- wait 10000µs
- CLK UP
- wait 5000µs
- CLK_DOWN
- CLK_UP
- CLK_DOWN
- CLK_UP
- wait 5000µs
- CLK_DOWN
- CLK_UP
- CLK_DOWN
- wait 150 µs
- disable VDD
- wait 250 µs
- disable VPP

---------

complete IC (PFS154) was erased *EXCEPT* 3 words stayed constant:
@0x7ED : 0x0281    => RET 0x81
@0x7EF : 0x027A    => RET 0x7A
@0x7F0 : 0x1FFF    ? ? ? maybe a "magic value"

So looks like to identify a flash IC the 0x1FFF is detected (followed by 2 times erase counter, which was erased :-) )
The specific part is encoded @0x7ED, @0x7EF (guess: coded as "RET k" so calibration routine or user program can use it to identify IC it is running on) => IC type is 0x7A81 or 0x817A 

Have fun,

JS

EDIT: BONUS points: If erase counter is erased (0x3FFF) then it starts with 0 again when using original WRITER to program the IC. It made my test IC "virgin" again :-)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 03, 2019, 01:12:09 am
AFAIK that extra clock is needed by all commands. I'm not sure how you are being able to use the read with  12 bit reply in place of the 13 as the scope shows.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on January 03, 2019, 02:21:25 am
I am going to try using a DAC + opamp to generate the necessary variable voltages needed for programming. Driving a capacitive load with an opamp is generaly a bad idea - they will tend to oscillate. TI has a chip that they say is "awesome for driving capacitive loads!!!", so I am going to see if it really is. Hope to have all the parts in a few weeks.

http://www.ti.com/lit/ds/symlink/alm2402-q1.pdf (http://www.ti.com/lit/ds/symlink/alm2402-q1.pdf)
http://www.ti.com/lit/ds/symlink/dac084s085.pdf (http://www.ti.com/lit/ds/symlink/dac084s085.pdf)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 03, 2019, 03:03:46 pm
AFAIK that extra clock is needed by all commands. I'm not sure how you are being able to use the read with  12 bit reply in place of the 13 as the scope shows.

After looking at the captures some more time it looks like the following happens:

Example PFS154 READ:

>preamble 28 bit
>command 4 bit
- 4 clocks
<ack 12 bit
- 1 clock
>addr 13 bit
<data 14 bit
- 1 clock
>addr 13 bit
< data 14 bit
- 1 clock
...
>addr 13 bit
< data 14 bit
- 1 clock

(It looks like whenever a switch from DAT-INPUT mode to DAT-OUTPUT mode is performed this extra "1 clock" is required)

My previous READ was working since I used 14 bit as address, which supplied the extra clock after switching DAT form input to output.

I will edit previous posts to have 13 bit address.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 04, 2019, 12:50:50 am
Still not fully done...

I changed my READ to use 13 bit and sending extra clock.

Now I have a very reliable READ and ERASE.

However the WRITE is not working yet. Not a single bit is written. I massaged my DAT/CLK output to be almost identical to the one from WRITER.
The only difference I found is that it looks like after WRITER sent command "WRITE" VPP gets increased to 8V followed by delay of 5ms (maybe waiting for stabilization) and then (different to ERASE) also VPP is increased to 5.6V followed again by a delay of 5ms (wait for stabilization...) and then data is sent.

In order to have this feature I need to add one more transistor and power rail to my bread board and also must put a level shifter between input pins / output pins of MCU and IC ... ?? really ??

Stay tuned...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: amyk on January 04, 2019, 02:57:48 am
Think of it this way: The official programmer wouldn't have done so if it wasn't required ;)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 04, 2019, 10:06:45 am
That's great work :-+ :-+ :-+ any progress regarding the OTP ones? also any other part in the family?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 04, 2019, 10:36:42 am
I could try running the SPI decoder on the OTP ones, but I'd need a scope dump first.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 05, 2019, 06:19:47 pm
Today, I made a first step to inefficently compiling a small subset of C to Padauk asm code. The current version is very restricted and generates very inefficient code; it is untested.

There is no assembler / linker support, so the resulting .asm file has to be assembled in other ways.

[…]

Code in svn at https://svn.code.sf.net/p/sdcc/code/branches/pdk/sdcc, use -mpdk14 to target Padauk (despite the name, the set of instructions emitted is part of the common subset of the Padauk instruction sets).

On the second day, wrt. completeness of implementation of the C standard, this has now far surpassed Mini-C.

Noticeable remaining restrictions:

* Variables can only reside in RAM, not in code space
* Global and static variables are not initialized.
* No floating-point or bit-fields.
* Functions can return at most 2 bytes (i.e. no long or long long).
* Multiplicative operators are not supported.
* Functions are not reentrant.
* No support for variable arguments.
* No standard library.
* struct / union cannot be assigned, passed as arguments or returned.
* No compoundliterals.
* No access to I/O from C.

There is no glue to connect this to assembler / linker yet, so the only useable output is asm code.
The generated asm code is still very inefficient. I will look into improving that a bit soon.

Philipp

Most of the above restrictions still apply.
There is now I/O support via __sfr, __sfr16.
There is rudimentary support for reentrant functions and variable arguments, but so far it only works for simple functions).

But there are still substantial improvements. There are fewer errors during compilation, the generated code is more efficient. A large part of the standard library (i.e. nearly everything that does not rely on return values > 16 bit) now compiles without errors.

My next main goals for this month are improving the support for reentrant functions / variable arguments, implementing initialization of global and static variables and getting something basic working for the glue between compiler, assembler and linker.

Philipp

P.S.:
At this point it would be really helpful for my work on sdcc if someone with access to the hardware could find out how push af works exactly.
Does a go to [sp] and f to [sp + 1]? Does a go to [sp + 1] and f to [sp]?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 06, 2019, 05:44:40 pm
A first usable version of the sampling software for my ADC4 board is done with the 1 GB RAM. As always needed a bit longer than expected, not as easy as it should be to access DDR3 RAM from a FPGA. I included a test mode which saves a counter in the RAM to check it, and also a CRC8 checksum because I'm transferring it over an external serial port connection. Sometimes there are transfer errors, but the CRC8 checksum detects it and I transfer the block then again. So the data should be very accurate.

I recorded the programming cycle of a PMS150C with SOT-23-6 package. There is no extra information with 25 MHz, so I used 12.5 MHz samplerate.

I stored the data in Sigrok format to view with PulseView (https://sigrok.org/wiki/PulseView), which is the best open source program for viewing analog data that I could find. It works for Windows, Linux and Mac. I couldn't find a way for GTKWave to show voltage divs. PulseView forgets the settings always when you load a new file, but at least it can be configured with 1 V per div and horizontal lines for each div, and navigating even in big datasets is fast and smooth. This is an example how you configure it when you click on the channel arrow:

(https://i.imgur.com/Jt9tzND.png)

You can also see the cursor, which is enabled by clicking on the blue cursor symbol in the toolbar, and which is useful for measuring time deltas.

All files are here:

http://www.frank-buss.de/tmp/dumps.zip (http://www.frank-buss.de/tmp/dumps.zip)

A *.sr file is just a zip file, and the analog-1-1-1 files are binary files of the voltages, with 4 byte float values for each sample, which could be converted back to float in Python with struct.unpack. But for easier reading I stored it in CSV format as well. The files in detail:

blinker.zip: the Padauk project and PDK file, compiled with IDE version 0.84
dump1.sr/csv: programming an already programmed PMS150C OTP chip with the blinker OTP. The following signals are connected to the channels:

CH1: PA4
CH2: PA6
CH3: VDD
CH4: PA5

The full sequence looks like this:

(https://i.imgur.com/biGVOAK.png)

PA5 (CH4) doesn't look very interesting. So for the next files dump2.sr/csv, I sampled the following signals, now using CH4 for PA3:

CH1: PA4
CH2: PA6
CH3: VDD
CH4: PA3

It looks like this:

(https://i.imgur.com/n1F36RA.png)

You can use the signals which are identical in the two dumps to correlate the PA5 signal in relation to PA3, if needed.

Then I used an empty chip and programmed it and saved it as dump3. The channel configuration is the same as used first:

CH1: PA4
CH2: PA6
CH3: VDD
CH4: PA5

It needs longer, so I sampled 2 seconds, with the same resolution of 12.5 MHz samplerate as the other dumps. Looks like this:

(https://i.imgur.com/GZMhY5a.png)

Finally I used another empty chip and programmed it, and saved the dump as dump4, now recording PA3 again instead of PA5 with CH4:

CH1: PA4
CH2: PA6
CH3: VDD
CH4: PA3

Looks like this:

(https://i.imgur.com/wjevexw.png)

I don't have much time to analyze it myself, but I guess now it shouldn't be too difficult to reverse engineer the full protocol.

PS: I disabled the open/short test with the ".writer" directive in the blinker.PRE file, because there were some problems with it with the SOT23-6 to DIP14 adapter, so some details of the dump might be different compared to the other dumps.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 06, 2019, 06:40:22 pm
Thank you, that is extremely useful.

From a first glance, the programming interface of the PMC150 seems to be straight forward. The main difference to the PFS154 is that it does not seem to use a bidirectional data line, but a normal SPI interface.

My guess is that the pinout is as follows:


The program mode entry sequence is very similar to the PFS:


VPP is 7.5V during read and ~10.5V during writing. This seems rather low. Are the ADCs calibrated correctly or may there be some offset/gain error?

VDD is 6V during programming, 4V during reading and 2V for verification. I would guess that it should be ok to keep VDD at 5V if you don't want to verify all corner cases.

To understand the protocoll it will be necessary to extract the logs using an SPI protocol analyzer. I will try to use PulseView for that. I am using it for the first time. It looks nice, but seems to be lacking some functionality. For example, how is it possible to display voltage values of specific data points`?

Edit: One comment: I find the entry sequence rather odd. Usually you would try to avoid under all circumstances applying a high voltage to a CMOS input when VDD is not connected due to latch up risk and potential damage to the ESD circuit. The programmer needs to control this sequence carefully to prevent frying the device.

-
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 06, 2019, 10:02:28 pm
A first usable version of the sampling software for my ADC4 board is done with the 1 GB RAM.

Not to nit-pick, but it seems there is a lot of cross talk and bouncing going on. Also clock and data seem to be out of phase in some areas.
Don't if that is really the case or if the data for the otp is really that different from the pfs154.

Have you tried to sample test signals?
Ie clock of a micro on one channel and look what the rest does?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 06, 2019, 11:31:58 pm
VPP is 7.5V during read and ~10.5V during writing. This seems rather low. Are the ADCs calibrated correctly or may there be some offset/gain error?

VDD is 6V during programming, 4V during reading and 2V for verification. I would guess that it should be ok to keep VDD at 5V if you don't want to verify all corner cases.

To understand the protocoll it will be necessary to extract the logs using an SPI protocol analyzer. I will try to use PulseView for that. I am using it for the first time. It looks nice, but seems to be lacking some functionality. For example, how is it possible to display voltage values of specific data points`?


There could be an error of about 0.1 V - 0.2 V, the potentiometers are a bit sensitive, and it clips at about 10.24 V: Everything higher than this is 10.24 V. Maybe I should calibrate it for 12 V, but then the resolution gets worse.

But I verified PA5 (right, looks like VPP) with my Agilent scope and the rest should be pretty accurate. From dump3 with PulseView:

(https://i.imgur.com/Ci5YJNT.png)

And you are right, PulseView is very limited. I couldn't find a way to read the exact voltages at a location. When you move the mouse over a location, it shows it in millivolt if it is below 1 V, and only if zoomed in like crazy, and if it is above 1 V, it is rounded to closest integer values. Looks like the programmers never used a real scope  :palm: But the workaround I described works pretty well: click on the channel label, then set "number of pos vertical divs" to 10, and vertical resolution to 1 V / div. Then you will have at least each 1 V div a horizontal line.

This is how it looks like when I record it with my scope. Not the same recording sequence, but again programming an empty chip:

(https://i.imgur.com/faSjHIX.png)

As you can see, the 7.5 V is about the same, and then you can see the clipping.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 06, 2019, 11:34:53 pm
Ah, interesting, that makes a lot of sense. Have you checked what the actual VPP is, instead of 10.5V? I suppose it is 12V or higher?

I got pretty far decoding the protocol, I am mainly stuck at writing right now. I will post my notes soon.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 06, 2019, 11:48:42 pm
Not to nit-pick, but it seems there is a lot of cross talk and bouncing going on. Also clock and data seem to be out of phase in some areas.
Don't if that is really the case or if the data for the otp is really that different from the pfs154.

Have you tried to sample test signals?
Ie clock of a micro on one channel and look what the rest does?

You are right, cross talk is terrible. But I think the recording should be very accurate regarding the timing and the phase of the signals.

I verified it with my signal generator and because of the nature of the sampling on the FPGA it is very unlikely that there is a phase error. But of course there could be still bugs in the Python script etc. If you think there are any wrong or strange signals, I can record any 2 signals with my real oscilloscope to verify it. This is a screenshot of my oscilloscope Python script, with 4 Vpp and 500 kHz from the signal generator, channel 2 phase shifted 180°:

(https://i.imgur.com/2upAumM.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 06, 2019, 11:53:49 pm
You are right, cross talk is terrible. But I think the recording should be very accurate regarding the timing and the phase of the signals.

From what I see, there is mainly crosstalk from Clk to VDD and MISO/MOSI. I suppose this crosstalk could also be internal to the MCU (from CMOS switching), since it is fully clocked externally in programming mode. Apart from the truncation of Vpp voltage, the logs look fine to me.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 06, 2019, 11:58:32 pm
Have you checked what the actual VPP is, instead of 10.5V? I suppose it is 12V or higher?

This is the full cycle of VPP with my scope:

(https://i.imgur.com/qeU5it4.png)

I verified it and the scope has no problems to measure more than 12 V, no clipping here. So it looks like the max level is about 10.8 V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 12:02:22 am
PS: I noticed that it looked like the programmer loads a new firmware when I switch from the PMS150C to the PMC884. So it is plausible that some parts of the programming sequence are very different depending on the chip.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 07, 2019, 02:48:51 am
Please find attached my notes on analysing the programming sequence from Frank. Sorry for the bad image quality, I had to limit the filesize. I can upload it somewhere else later.

The information is not yet very structured, but I believe it should be enough to create a programmer for the PMS150C from scratch.

Something I have not yet looking into, is the clock calibration/code checksum. So, for a start, it would be easier to generate binaries without the initialization code that the Padauk IDE adds.

Many parts of the programming sequence are only to verify operation at different corner cases of the operating voltage. It is probably sufficient to stay at a single level of VDD, e.g. 5V.

A challenge that remains will be to come up with hardware that allows controlling VPP at 7.5V and 10.8V. Maybe some of the existing PIC programmers can be used as a reference.

Btw, one issue that could also be existent with the PFS154 is a strange behavior of MISO during data direction changes (see slides 12/13). Many bidirectional protocols (e.g. SWD) introduce an additional cycle for direction reversal. Padauk has omitted this, which leads to unexpected "features". Generally,  there are some parts of the protocol that look like workarounds. I'd guess they fixed things as they come, so probably there are also some inconsistencies between devices.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 05:58:54 am
Please find attached my notes on analysing the programming sequence from Frank.

Great work! The different programming voltages shouldn't be a problem. The circuit diagram from @oPossum looks good, the ALM2402 can drive up to 400 mA, so maybe no external transistor amplifier is even needed. But it has only a gain bandwidth of 600 kHz, maybe would be good to use some additional 4051 for the high frequency data lines. Could be all controlled with a cheap Arduino nano, and a simple Python script to control it and send the programming file over serial port.

I wonder why they do all these tests. I guess they don't do much tests when they produce the ICs? So far I've used about 20 PMS150C for testing, programming little things etc. One IC was not programmable. Might be a good idea if a DIY programmer would do all the verifies at different voltage levels etc. as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 10:22:19 am
Hi,

Thanks @FrankBuss for the new captures and @tim_ for having a look at them. This confirms our previous findings of VDD/VPP sequence, CLK/DAT usage and some of the deciphered commands (READ/WRITE).
The only difference is that PMC150 just uses 12 bit address and 13 bit program words and that IC_DAT_IN and IC_DAT_OUT might be 2 different pins instead of 1 shared pin on PFS154.

JS

BTW: @tim_ (cpldcpu): Do you think it is ok to claim that this all your own work, based on captures from FrankBuss?
from page 2: > All of this work is solely based on analyzing datalogs of the programming sequence as provided here: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917)
Maybe next time you could also mention the work of the eevblog forums community members.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 10:48:37 am

The different programming voltages shouldn't be a problem. The circuit diagram from @oPossum looks good, the ALM2402 can drive up to 400 mA, so maybe no external transistor amplifier is even needed. But it has only a gain bandwidth of 600 kHz, maybe would be good to use some additional 4051 for the high frequency data lines. Could be all controlled with a cheap Arduino nano, and a simple Python script to control it and send the programming file over serial port.

I wonder why they do all these tests. I guess they don't do much tests when they produce the ICs? So far I've used about 20 PMS150C for testing, programming little things etc. One IC was not programmable. Might be a good idea if a DIY programmer would do all the verifies at different voltage levels etc. as well.

Over the weekend I spent some time with a friend to create a simple and cheap programmer schematic based on all the suggestions from this thread :):
- we did it as an experiment to use only free tools and the cheap supply chain from LCSC / JLPCB
- so we used EASY-EDA with LCSC parts and plan to use JLPCB (they all belong together)
- PCB + all parts will be around $5
- the programmer does not require an external power supply (it creates +15V from USB)
- it uses a STM32F072 which has 2x 12 bit DAC outputs to generate reference voltage for VDD and VPP which are then supplied to an opamp
- stability and level of the output voltages is measured with 2 ADC channels and can be tuned live
- for input/output to IC, 5 volt tolerant pins are used on STM32F072 (max. 5.5V)
- after checking programing of several different IC types we are pretty sure that DAT from IC to WRITER never exceeds VDD and max VDD we saw was 5.6V (no level shifter required)

What do you think?

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 11:37:01 am
The STM32 does only output 3.3V. It might work, but would be better to use a 4053, costs only 35 cent (https://www.digikey.de/short/p7q44b) (probably cheaper at LCSC) and has 3 switches, with which you could select VDD or GND for the data lines. Maybe there are even low cost multi channel voltage converters, but you can get the 4053 everywhere. If it works with 5 V for VDD, then at least you don't need extra ICs when the IC sends data back, because the IOs of the STM32 are 5 V tolerant. But they might might not like the 6.5 V we've seen with the PMS150C. With your current schematic it is possible to set a higher voltage on VDD. Always good to design a circuit in a way that no matter how buggy the firmware is, the hardware doesn't get destroyed :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 07, 2019, 11:40:40 am
I'm not sure using a STM32 is the best option if it's designed to be hand assembled by hobbyists. TSOP aren't particularly friendly.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 12:18:00 pm
I'm not sure using a STM32 is the best option if it's designed to be hand assembled by hobbyists. TSOP aren't particularly friendly.

It is a LQFP package. For me it is easier and faster to solder than DIP packages. @EEVblog did a video about it:

https://www.youtube.com/watch?v=hoLf8gvvXXU (https://www.youtube.com/watch?v=hoLf8gvvXXU)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 07, 2019, 12:28:25 pm
STM32 is fine, but maybe a STMF0 or STMF1 would cost even lower! ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 12:29:49 pm
The STM32 does only output 3.3V. It might work, but would be better to use a 4053, costs only 35 cent (https://www.digikey.de/short/p7q44b) (probably cheaper at LCSC) and has 3 switches, with which you could select VDD or GND for the data lines. Maybe there are even low cost multi channel voltage converters, but you can get the 4053 everywhere. If it works with 5 V for VDD, then at least you don't need extra ICs when the IC sends data back, because the IOs of the STM32 are 5 V tolerant. But they might might not like the 6.5 V we've seen with the PMS150C. With your current schematic it is possible to set a higher voltage on VDD. Always good to design a circuit in a way that no matter how buggy the firmware is, the hardware doesn't get destroyed :)

Hi,

from datasheet of STM32F072:  5 volt tolerant pin VMax = VDDIO + 4.0 V,  VDDIO = 3.3V ==> absolute maximum is 7.3 volt.

So should be no problem. Right ?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 12:46:42 pm
from datasheet of STM32F072:  5 volt tolerant pin VMax = VDDIO + 4.0 V,  VDDIO = 3.3V ==> absolute maximum is 7.3 volt.

So should be no problem. Right ?

This is for the absolute maximum ratings, which means the IC might not get damaged if below, but I wouldn't use this as a limit. In the table "general operation condition" the max value for the FT (5 V tolerant) pins is 5.5 V. And I'm not sure, if both conditions must be met, which would mean you can use VDDIO+4V, unless it is below 5.5 V. Might be worth to ask ST, they have a good customer support.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 07, 2019, 12:51:20 pm
You can just use two clamping diodes with low Vf from the data pins to VCC along with some low-value (100ohm) current-limiting resistors to ensure it never goes above the limit.

The STM already has such clamping diodes inside the MCU but I'm not sure if I'd trust them for other than short transients.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 01:01:21 pm
Why a low resistor? I think something like attached would work perfectly, but might be not needed, if 5 V for VDD works.

Edit: for the bidirectional pins, you might need a 4052 to select VDD, GND and open or pullup.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 07, 2019, 01:11:53 pm
Lower values means faster transitions and less ringing on the data lines. I always prefer to use the lowest value possible, just to ensure funny things doesn't happen because of that ringing. It's a bit too low specially since I realized it's 3.3V and then it'll be sinking more than the 20mA recommended by the STM datasheet.

10kOhm could work, that's the recommended value for 100kHz I2C buses. I'm guessing programming them at 100kHz is good enough.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 07, 2019, 03:24:06 pm
I think something like attached would work perfectly, but might be not needed, if 5 V for VDD works.
I think your solution with the 4053 is a good idea.

But the 5V supply is directly from the VUSB. There are often polyfuses in the USB host port, wire resistance,... in the way, so VUSB is often more like 4.6V oder 4.5V in the end. While true 5V might work, I fear the lower real voltage won't.

So why not use a small linear regulator with variable output voltage, like an 1117-ADJ, to create the Vdd for the 4053 out of the 15V from the boost regulator? Then you can set the necessary voltage with a voltage divider. A cheap regulator that should work, available from LCSC, would be for example the MET1117FB3G. Others are available too, but some don't allow 15V input voltage.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 04:00:16 pm
Hi,

When I checked STM32F072 was cheapest option:
LCSC:
 STM32F072C8T6: 1+ €1.2514, 10+ €1.2096, 100+ €1.0841
 STM32F103C8T6: 1+ €1.8233, 10+ €1.3186, 30+ €1.2260

Considering that the PADAUK IC can be operated with 2.0 V I don't know how the above mentioned circuit from FrankBuss would perform with lower 1 voltage levels.

I'm not sure how to enable/disable individual pins of the output level shifter to stop outputting 0 or 1 when the pins are in input mode for writer. ? ? ?

A level shifter can use the same VDD which is supplied to PADAUK IC.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 07, 2019, 04:42:36 pm
But the 5V supply is directly from the VUSB. There are often polyfuses in the USB host port, wire resistance,... in the way, so VUSB is often more like 4.6V oder 4.5V in the end. While true 5V might work, I fear the lower real voltage won't.

The USB standard allows voltages down to 4.4V at the device side end of the cable. So any programmer powered from USB should be able to deal with that.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 04:52:34 pm
I'm not sure how to enable/disable individual pins of the output level shifter to stop outputting 0 or 1 when the pins are in input mode for writer. ? ? ?

You could use a 4051, cheap at LCSC:

https://lcsc.com/product-detail/4000-Series_NXP_HEF4051BT_HEF4051BT_C11351.html

You would need one 4051 per logic pin on the Padauk IC. You could then select 4 different things: VDD, GND, pullup to VDD and pulldown to GND. Would need 2 output pins from the STM32 and one input pin with the previous circuit with the resistor and diode to sense the voltage when the Padauk IC is sending back information, for each logic pin of the Padauk IC. It is no problem to switch voltages down to 2 V would work up to 15 V. But if it goes down to 2 V, the power supply for the IC would still need 3 V. So I would connect VDD of the 4053 to 15 V.

I guess only the VDD, pullup and GND would be needed, because the analysis from tim showed that the small pin count Padauk ICs like the PMS150C pulls down bidirectional lines, and the higher count ICs might use dedicated pins for in/out and no bidirectional pins. But this could be used to program chips from other manufacturers as well, where it might be useful to switch it to a pulldown resistor.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 07, 2019, 05:00:57 pm
BTW: @tim_ (cpldcpu): Do you think it is ok to claim that this all your own work, based on captures from FrankBuss?
from page 2: > All of this work is solely based on analyzing datalogs of the programming sequence as provided here: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917)
Maybe next time you could also mention the work of the eevblog forums community members.

I think I should have been more clear in outlining the purpose of the disclaimer on page 2. I added it to emphasize that this is  a clean room analysis  (https://en.wikipedia.org/wiki/Clean_room_design) of the protocol that is based only on behavioral observation and not on code reverse engineering. The latter may be illegal in some countries. I doubt Padauk cares much, but better safe than sorry. I would not like to see anyones effort be targeted by a C&D. It cleary was not meant to credit or discredit anyone.

JS, your work is extremely appreciated and this would have not been possible without yours and others prior work.

I update the wording on the slides a bit to avoid further confusion.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 07, 2019, 05:16:47 pm
Hi,

When I checked STM32F072 was cheapest option:
LCSC:
 STM32F072C8T6: 1+ €1.2514, 10+ €1.2096, 100+ €1.0841
 STM32F103C8T6: 1+ €1.8233, 10+ €1.3186, 30+ €1.2260


I guess Padauk looked at the same price list, because the original programmer uses a STM32F072 as well  :)

https://i.imgur.com/EQn3HHS.jpg

And it uses a few 4051, so maybe similar ideas which I have, but interestingly a 4066 CMOS switch, too:

https://i.imgur.com/EfprDYv.jpg

The markings for the chip on the right side are difficult to read, I can't see it, but might be another of these multiplexers/switches:

https://i.imgur.com/d1tatL0.jpg

PS: With a 4051, and switching to pullup, pulldown, VDD and GND, and in combination with regulated VDD and using the STM32 pins in analog input mode, it wouldn't be difficult to implement the open/close functionality in software.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 07, 2019, 05:33:20 pm
How about an Arduino based programmer?  :D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 05:42:13 pm
PS: With a 4051, and switching to pullup, pulldown, VDD and GND, and in combination with regulated VDD and using the STM32 pins in analog input mode, it wouldn't be difficult to implement the open/close functionality in software.

Hi,

I'm not sure if the analog input is fast enough. If you use 14MHz analog clock and 1.5 analog clock cycles for conversion the result is very noisy. You start to get good results at 70+ cycles.

Today I will do some experiments to get WRITE working without a level shifter and check the result. I will use several voltages for VDD and check at which voltage the STM gets damaged. Then we can decide if lower part count or more stability is the way to go.
Adding several 4051 will use a lot of board space which I wanted to keep small initially.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 07, 2019, 05:43:13 pm
I update the wording on the slides a bit to avoid further confusion.

All is fine. Big hug!

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 07, 2019, 06:25:15 pm
Adding several 4051 will use a lot of board space which I wanted to keep small initially.
I can understand that.

How about a solution with simple discrete mosfets like in the attached schematic?

Simple mosfet like BSS138 and BSS84 cost less than 2 cent at LCSC and allow +-20V Vgs without damage. They also switch low currents reliably at 3.3Vgs. They are in SOT-23, that doesn't take much space and is easy to solder. You can also get them in SOT-323 or two mosfets in one SOT-23-6 / SOT-323-6, but these are a few cents more.

You'd need 3 pins on the STM32 for each pin on the PADAUK, but I think the LQFP-48 of the STM32 has enough pins to spare.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 07, 2019, 06:29:53 pm
Hi,

When I checked STM32F072 was cheapest option:
LCSC:
 STM32F072C8T6: 1+ €1.2514, 10+ €1.2096, 100+ €1.0841
 STM32F103C8T6: 1+ €1.8233, 10+ €1.3186, 30+ €1.2260


You do know that a whole board with STM32F103C8T6 can be had for $1.60 shipping included? Ready to run with arduino.

https://de.aliexpress.com/item/STM32F103C8T6-ARM-STM32-Minimum-System-Development-Board-Module-Forarduino/32342717171.html

Maybe create just a shield for that?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 07, 2019, 06:34:44 pm
You do know that a whole board with STM32F103C8T6 can be had for $1.60 shipping included?
The STM32F103C8T6 doesn't have DACs, the STM32F072 has. You'd need to use PWM with feedback which makes reaching the desired voltages much slower.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 07, 2019, 06:43:39 pm
Some ideas can be captured from j-link, especially the clone ones! us normal 74HC series to do the conversion and level shifting,it's cheap also ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 07, 2019, 06:55:37 pm
How about an Arduino based programmer?  :D
That would be much easier, easily built in a breadboard and protoboard with only DIP parts, and it's probably the way I'm gonna try doing this.

My idea so far is using an external 12V supply for now (maybe later upgrade it to a SMPS feeding from the USB 5V), and use a few linear regulators with resistors for stepping down to a few preset voltages. It'll be a while until I try it though however, I still haven't even put the order for the PFS154 parts lol.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 07, 2019, 07:05:10 pm
Well, you could use a very simple boost converter that is driven by a PWM output of a microcontroller... Seems to work well.

Note that VPP can be controlled by the frequency and duty cycle of V1. No need for a DAC and OPAMP.


(https://i.imgur.com/JkA1XrN.gif)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 07, 2019, 07:22:32 pm
You do know that a whole board with STM32F103C8T6 can be had for $1.60 shipping included?
The STM32F103C8T6 doesn't have DACs, the STM32F072 has. You'd need to use PWM with feedback which makes reaching the desired voltages much slower.

The board has more than enough IO pins > 30 if i rember correctly.
We already concluded that VDD only needs .1 V steps over the range from 2 to 5.6V thats ~ 6 pins necessary. Vpp can be very coarse from 5.6 to 12 V lets say 3 pins.
Feedback by analog converter is only needed once (on startup for example) to save on precision resistors.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 07, 2019, 07:28:19 pm
FWIW I started building and successfully tested a charge pump / PWM based voltage supply for both Vdd and Vpp with feedback by ADC on an arduino.
Its to slow to work without transistors to switch the supplies on/off but otherwise works quite nicely. Even with a simple breadboard.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 07, 2019, 07:50:06 pm
FWIW I started building and successfully tested a charge pump / PWM based voltage supply for both Vdd and Vpp with feedback by ADC on an arduino.
Its to slow to work without transistors to switch the supplies on/off but otherwise works quite nicely. Even with a simple breadboard.

A charg pump or boost converter? Note that in both cases your could use a (software-) PD controller to speed up the step response significantly.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 07, 2019, 07:55:09 pm
A charg pump or boost converter? Note that in both cases your could use a (software-) PD controller to speed up the step response significantly.

charge pump with I should say trivial software right now, however the problem is getting from 0 to target voltage which takes ~ 50 ms I think and thats something a pd controller cant help with ;)
Thats why I just switch the output.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 08, 2019, 11:35:53 pm
I had some success with a programmer based on an Arduino Nano, see image. It is using a simple boost converter that is controlled by a PWM output and monitored with the integrated ADC, similar to the PIC programmer that someone linked earlier in this thread. You can find the actual circuit I use in the LTspice simulation I posted above. The PWM duty cycle can be used to control VPP between 4.3V and >12V. VCC is directly connected to a GPIO, so VCC is always 5V. MISO/MOSI/SCLK are directly connected to GPIO.

What works:

See below for a log. The cells below <0x40 have been writte to by the programmer. Device is a PMS150C, btw.

Open:
- The control of the boost converter is not optimzed yet. By using a closed loop controller it should be possible to improve settling time.
- It appears that data needs to be written twice. I am not sure whether this is some kind of initialization issue or whether VCC needs to be increased to 6V as in the original programmer for more reliable programming.
- I have not tested writing actualy code to the device.

I noticed some oversights in my earlier analysis, which have been corrected in the attached pdf.

I also attached a part of the source, for reference. It's basically only some disconnected routines with prinft debugging.. What is still completly missing is the interaction with a host computer, so this is still very far from a proper programmer.

(https://i.imgur.com/yRKITv3.jpg)

Code: [Select]
Initializing...
DeviceID: A16   Vpp Standby: 376
Dumping memory...
Vpp read mode: 547
0000: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0010: 01AA 0155 1FFF 1FFF 1A5A 15A5 1FFF 1FFF 1A5A 15A5 1A5A 15A5 1FFF 1FFF 1FFF 1FFF
0020: 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5
0030: 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5 1A5A 15A5
0040: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0050: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0060: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0070: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0080: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0090: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00A0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00B0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00C0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00D0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00E0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
00F0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0100: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0110: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0120: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0130: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0140: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0150: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0160: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0170: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0180: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0190: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01A0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01B0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01C0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01D0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01E0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
01F0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0200: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0210: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0220: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0230: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0240: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0250: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0260: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0270: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0280: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0290: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02A0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02B0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02C0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02D0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02E0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
02F0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0300: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0310: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0320: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0330: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0340: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0350: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0360: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0370: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0380: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
0390: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03A0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03B0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03C0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03D0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03E0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF
03F0: 1FFF 1FFF 1FFF 1FFF 1FFF 1FFF 018A 1FFF 1FFF 1FFF 1FFF 1FFF 0FFF 1FFF 1FFF 0FFD
Writing to memory...
Vpp initial: 541        PWM: 10
Vpp write mode: 792     PWM: 42
Vpp after writing: 793
Vpp off: 396

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 09, 2019, 12:02:22 pm
Thanks for your findings and implementation.  :clap:

In fact it matches my experiments but for some reason it does not work on PFS154 yet. After I converted my project to support also the small 13 bit devices I was able to program PMC150 immediately like you did.
So only the shared DAT pin for input and output on PFS154 still troubles me a bit.

JS

EDIT: What you call "Device-ID" seems to be the "ACK" we seen on PFS154.
on PFS154:

after a command is sent you need to send some dummy clocks (4) for the IC to process the command
-> maybe some more clocks are required on PMC150 which you call "dummy write"
then direction changes and and ACK is sent back (12 bit): 0xAA1
-> maybe on PMC150 it is 0xA1
then again a dummy clock is required before you can start sending data
-> maybe the "6" is just garbage since only 4 dummy clocks are needed.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 09, 2019, 12:41:28 pm
Hi,

I made some progress on the "easy pdk prog" programmer.

Based an the suggestions from you I added the transistor solution to shift the logic output voltage of the STM32.

I also created a PCB and sent the Gerber production files to JLPCB. They will manufacture 10 pcs for USD 2.00  :)
All the parts can be ordered from LCSC so I was able to combine this 2 orders which usually reduces shipping cost.
But I also got a discount for first time order which eliminated shipping cost at all.  ;D

The PCB only uses one side for components for better assembly but the size is still very small: 58mm x 22mm (slightly larger than arduino nano).

Features:
 - USB powered device (no extra power supply)
 - variable and monitored IC VPP (0-15V) to support all models (OTP and flash)
 - variable and monitored IC VDD (0-6V) for calibration of Padauk IC
 - output voltage level shift to support communication with any IC VDD (up to 6 V)
 - extra 8 MHz oscillator for calibration of Padauk IC
 - 3 user LED to show status
 - 1 button to start operations from programmer directly

Price for PCB + components is also very attractive (depends on how many pcs. you want to make):
 1  pcs: PCB: $ 2.00 , BOM: $ 2.39   => $ 4.39
10 pcs: PCB: $ 2.00 , BOM: $ 19.78  => $ 2.19 / pcs

Now need to wait 9-14 days for the stuff to arrive.

JS

BTW: The only thing I miss in EasyEDA is the feature to show components on the 3D rendering of the PCB. Everything else was easy to learn and very intuitive. Great job from them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 09, 2019, 01:00:02 pm
The HT7991 that you have used, can boost to 12V, it can not make 15V, simply replace it with MT3608, it can go upto 28v and it's super cheap ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 09, 2019, 01:15:59 pm
Things are looking awesome on all fronts!

Just a couple suggestions on the pcb:
- maybe leave unpopulated target footprints on the back, so we can program the most common parts by holding against those.
- maybe add a few pin connectors to the sides of the usb for mechanical support. This would allow target sockets to be firmly mounted on a shield-like pcb on top/bottom of the programmer.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 09, 2019, 01:40:23 pm
The HT7991 that you have used, can boost to 12V, it can not make 15V, simply replace it with MT3608, it can go upto 28v and it's super cheap ;)

Great find. It also looks pin compatible and we can save $0.02 :)  I will test it.

Just a couple suggestions on the pcb:
- maybe leave unpopulated target footprints on the back, so we can program the most common parts by holding against those.
- maybe add a few pin connectors to the sides of the usb for mechanical support. This would allow target sockets to be firmly mounted on a shield-like pcb on top/bottom of the programmer.

This is just a test PCB. Usually the first try always contains some mistakes (wrong foot prints in library, bad component spacing, something not working as expected, ... ). But since it costs $ 2.00 only... so what :)

I really like the idea to put a SOT foot print. We only need to decided which part we want to support since pins do shift a lot between different IC. I would vote for the flash parts (PFS...) since they might be the most popular for hobbyists.

My plan was to use some of this SOT to DIP sockets and connect jumper wires for different types easily:
https://detail.tmall.com/item.htm?id=522621435705 (https://detail.tmall.com/item.htm?id=522621435705)
https://www.aliexpress.com/item/SOP28-Adapter-Socket-DIP28-to-SOP16-SOP20-300mil-Chip-Programmer-20pin-Feet/32900927477.html (https://www.aliexpress.com/item/SOP28-Adapter-Socket-DIP28-to-SOP16-SOP20-300mil-Chip-Programmer-20pin-Feet/32900927477.html)


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 09, 2019, 02:37:07 pm
My plan was to use some of this SOT to DIP sockets and connect jumper wires for different types easily:
https://detail.tmall.com/item.htm?id=522621435705 (https://detail.tmall.com/item.htm?id=522621435705)
https://www.aliexpress.com/item/SOP28-Adapter-Socket-DIP28-to-SOP16-SOP20-300mil-Chip-Programmer-20pin-Feet/32900927477.html (https://www.aliexpress.com/item/SOP28-Adapter-Socket-DIP28-to-SOP16-SOP20-300mil-Chip-Programmer-20pin-Feet/32900927477.html)
Yes, I think something like this is cheap & conveniant and much more reliable than just a footprint to hold the ic against.

Regarding the different Padauk types and their footprints: Why not use exchangeable adapter pcbs like this:
- Take the 8 pins of your programmer board and solder pin header sockets on them
(like these: https://lcsc.com/product-detail/Female-Header_2-54mm-1-8P-Straight-Female-header_C27438.html (https://lcsc.com/product-detail/Female-Header_2-54mm-1-8P-Straight-Female-header_C27438.html))
- Make several small adapter pcbs which route the 8 programmer pins to the correct pin numbers of the Padauk-IC pinout you are targeting with this adapter pcb.
- The adapter pcb has pin header sockets on it in standard dip 2.54mm raster
- You plug one of the sockets linked above into the pin header sockets of the adapter pcb

That way you don't need to fiddle with jumper wires, you just have to plug in the correct adapter pcb. LCSC allows you to create panels with several different small pcbs in one 10x10cm pcb for the regular 2$ price. You just have to separate them with small milled slots and keep them together with tabs. So the programmer and adapter pcbs could be made together in one go without added cost.

BTW, as I'm mostly interested in the Padauks in SOT-23-6, does anybody know of a cheap SOT-23-6 adapter? The cheapest I could find were these
https://www.aliexpress.com/item//32851813673.html (https://www.aliexpress.com/item//32851813673.html)
https://www.aliexpress.com/item//32811278237.html (https://www.aliexpress.com/item//32811278237.html)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 09, 2019, 02:58:08 pm
BTW, as I'm mostly interested in the Padauks in SOT-23-6, does anybody know of a cheap SOT-23-6 adapter? The cheapest I could find were these
https://www.aliexpress.com/item//32851813673.html (https://www.aliexpress.com/item//32851813673.html)
https://www.aliexpress.com/item//32811278237.html (https://www.aliexpress.com/item//32811278237.html)

Looks like a good price. When I bought the adapter from Padauk, they sold it for USD 30.

I think the idea with the header sockets is the best, like the PICkit. For in-circuit flash ICs, you could just add some pin headers on your board, or use pogo pins. And if you want to program it standalone, then you can make some custom boards for it, even with the adapters soldered on it.

BTW, with JLCPCB you can select "Panel By JLCPCB". If you have like a small adapter board which fits multiple times on a 10 cm x 10 cm board, they do the panelization for you, without additional cost. This way one adapter would cost $2, but you might get like 40 mini boards for it, enough for everyone following this thread :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 09, 2019, 03:08:08 pm


Good job!

Regarding the pdf: on page 18 you write that the data is clocked out after the first write cycle and believe that its verification data.
I dont think so. The data comes from the internal shift register being used for SPI. The default value seems to be the device ID, after that the bits you shifted in are simply shifted out. Its very unlikely that this is intended for verification purposes.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 09, 2019, 03:46:11 pm
Regarding the IC adapters, if the chips can be in circuit programmed, then they are useless ;D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 09, 2019, 03:52:38 pm
Regarding the IC adapters, if the chips can be in circuit programmed, then they are useless ;D
I don't think you want 10V programming voltage anywhere on your regular circuit.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DocBen on January 09, 2019, 03:58:12 pm
Regarding the IC adapters, if the chips can be in circuit programmed, then they are useless ;D
I don't think you want 10V programming voltage anywhere on your regular circuit.

Actually the pfs173, pfs154 and probably others are
http://www.padauk.com.tw/upload/doc/PFS173_datasheet_v101_EN_20181113.pdf (http://www.padauk.com.tw/upload/doc/PFS173_datasheet_v101_EN_20181113.pdf)
page 100 ff

PMS150C as well
http://www.padauk.com.tw/upload/doc/PMS150C%20datasheet%20V105_EN_20181128.pdf (http://www.padauk.com.tw/upload/doc/PMS150C%20datasheet%20V105_EN_20181128.pdf)
page 68

Just have to take the necessary precautions ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 09, 2019, 04:50:33 pm
Quote
I don't think you want 10V programming voltage anywhere on your regular circuit.
hopefully the 10v is on the reset pin and it can be isolated from other parts of the circuit ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: anxzhu on January 09, 2019, 05:02:33 pm
 ;D More choices for in-circuit flash ICs.

 https://detail.tmall.com/item.htm?spm=a230r.1.14.1.1ac96b0c2rst9C&id=551218777266&ns=1&abbucket=6&skuId=3646781263915
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 09, 2019, 06:31:32 pm
Thanks for your findings and implementation.  :clap:

In fact it matches my experiments but for some reason it does not work on PFS154 yet. After I converted my project to support also the small 13 bit devices I was able to program PMC150 immediately like you did.
So only the shared DAT pin for input and output on PFS154 still troubles me a bit.

Interesting, so there is something about the PFS154. I'll give it a try.

I think it could be very helpful to take an analog log of the PFS154 writes sequence. Most likely it will also be possible to deduce the write direction from the analog voltages.
Frank, do you think you have a chance to do this? If you don't have any PFS154 I could send some to you.

EDIT: What you call "Device-ID" seems to be the "ACK" we seen on PFS154.
on PFS154:

after a command is sent you need to send some dummy clocks (4) for the IC to process the command
-> maybe some more clocks are required on PMC150 which you call "dummy write"
then direction changes and and ACK is sent back (12 bit): 0xAA1
-> maybe on PMC150 it is 0xA1
then again a dummy clock is required before you can start sending data
-> maybe the "6" is just garbage since only 4 dummy clocks are needed.

Well, there is a lot of evidence that this actually is some kind of device ID.

- The code is read in the first step of the programming sequence (phase 0)
- The code is 0xA16 for the PMS150C. This bit sequence does not appear in the magic key (0XA5A5A5A7). Therefore it is unlikely that this is garbage information from the SPI shift register.
- Also, the signaling scheme to read it is exactly identical to the programmin sequence, except that the "write execution sequence" is not sent.

It would be interesting to read this code from other devices as well.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 09, 2019, 06:32:38 pm

Regarding the pdf: on page 18 you write that the data is clocked out after the first write cycle and believe that its verification data.
I dont think so. The data comes from the internal shift register being used for SPI. The default value seems to be the device ID, after that the bits you shifted in are simply shifted out. Its very unlikely that this is intended for verification purposes.

Indeed, you are right. This is the most likely explanation - and also the easiest way of implementing a device-ID, taking zero additional logic gates :)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 09, 2019, 07:46:11 pm
I think it could be very helpful to take an analog log of the PFS154 writes sequence. Most likely it will also be possible to deduce the write direction from the analog voltages.
Frank, do you think you have a chance to do this? If you don't have any PFS154 I could send some to you.

Yes, I can do this. I have only PMS150C and PMS154B, but I guess a flash version can be very different. If you want to send me a few, my address is on my impressum page: http://www.frank-buss.de/impressum.html (http://www.frank-buss.de/impressum.html) Would be faster than when I'm ordering it at lcsc, if you have already some. How many signals should I sample? Just asking in case I need to solder the second board, for a full 8 channel version of my ADC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 12:59:12 am
So I did some experiments with the PFS154. The protocol is slightly different indeed.

- As you described, the PSF154 needs to be clocked for 4+12=16 cycles after the magic-key/command. This sequence is not needed in the PMS150C.
- The response seems to be 0xFAA1 for a write or 0x1AA1 for a read. It is possible that the upmost 4 bit of this word are indeed random data.
- Address and command are both 14 bit.
- The device-id sequence of the PMS150 is missing in the PFS154. This is obvious, since the same scheme would not be supported with a single data line.
- The write instruction writes 4 instead of 2 words at once.

I was able to write to the memory, as you can see in the dump below. However, for some reason the data came out garbled. Only bits 4-11 were written to and the data was shifted by one bit. Really weird, since the address was actually correct. The write was 1A5A 15A5 0000 0000 to 0x38 and 0x40.

I also encountered a weird issue with the power up sequence. It appears the PFS154 was drawing a lot of power when VDD was grounded and VPP was ramped up. I was able to solve this by floating VDD during the VPP ramp and only pulling it to ground for a short time to reset the MCU. This reason for this could be latch up.

Tomorrow I will send some devices to Frank. It will be very helpful to get another datalog.

Code: [Select]
Initializing...
372 400 425 449 472 491 510 527 543 ACK: FAA1
DeviceID: 0     Vpp Standby: 373
Dumping memory...
372 400 425 449 472 492 510 527 543 ACK: 1AA1
Vpp read mode: 560
0000: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0010: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0020: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0030: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 34BF 3B4F 300F 300F 3FFF 3FFF 3FFF 3FFF
0040: 34BF 3B4F 300F 300F 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0050: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0060: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0070: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0080: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0090: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0100: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0110: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0120: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0130: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0140: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0150: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0160: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0170: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0180: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0190: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0200: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0210: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0220: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0230: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0240: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0250: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0260: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0270: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0280: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0290: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0300: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0310: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0320: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0330: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0340: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0350: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0360: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0370: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0380: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0390: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0400: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0410: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0420: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0430: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0440: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0450: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0460: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0470: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0480: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0490: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0500: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0510: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0520: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0530: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0540: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0550: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0560: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0570: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0580: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0590: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0600: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0610: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0620: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0630: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0640: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0650: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0660: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0670: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0680: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0690: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0700: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0710: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0720: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0730: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0740: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0750: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0760: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0770: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0780: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0790: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 0282 025A 1FFE
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
Writing to memory...
374 402 428 453 476 496 515 532 ACK: FAA1
Vpp initial: 536        PWM: 9
553 563 572 Vpp write mode: 595 PWM: 13
Vpp after writing: 580
Vpp off: 312

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 01:24:37 am
I think it could be very helpful to take an analog log of the PFS154 writes sequence. Most likely it will also be possible to deduce the write direction from the analog voltages.
Frank, do you think you have a chance to do this? If you don't have any PFS154 I could send some to you.

Yes, I can do this. I have only PMS150C and PMS154B, but I guess a flash version can be very different. If you want to send me a few, my address is on my impressum page: http://www.frank-buss.de/impressum.html (http://www.frank-buss.de/impressum.html) Would be faster than when I'm ordering it at lcsc, if you have already some. How many signals should I sample? Just asking in case I need to solder the second board, for a full 8 channel version of my ADC.

Thanks a lot! I will send out the devices tomorrow. The PFS154 is only using 4 wires (+gnd) instead of 5 like the PMS150C (see slide 4 in attachment). So your existing hardware should be fine.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on January 10, 2019, 12:14:07 pm
The circuit diagram from @oPossum looks good, the ALM2402 can drive up to 400 mA, so maybe no external transistor amplifier is even needed. But it has only a gain bandwidth of 600 kHz, maybe would be good to use some additional 4051 for the high frequency data lines.

At the time I designed that it wasn't clear if two programmable voltages would be enough, so I used four. I didn't intend to use the DAC for clock or data lines. I will probably be using 74LVCH1T45 for level translation of clock and data lines.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 12:47:40 pm
I also managed to read and write the PMS154C now. It uses the same protocol as the PMS150 (6 wire). Adresslength is 12, instruction length 14.
The deviceID is 0xE06, which is different from the 0xA16 of the PMS150C. This seems to confirm that this value is indeed a device ID.

Curiously a lot of memory cells were already written on the fresh device. See dump below. I only wrote to 0x20-0x27. So even at 0x00 there was a prior value programmed. Ideas anyone?

Code: [Select]
Initializing...
DeviceID: E06   Vpp Standby: 5.4
DeviceID is match to:PMS154C
Dumping memory...
Vpp read mode: 7.7
0000: 37E8 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0010: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0020: 1A5A 15A5 3FFF 3FFF 1A5A 15A5 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0030: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0040: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0050: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0060: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0070: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0080: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0090: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0100: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0110: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0120: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0130: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0140: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0150: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0160: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0170: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0180: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0190: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0200: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0210: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0220: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0230: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0240: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0250: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0260: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0270: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0280: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0290: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0300: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0310: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0320: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0330: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0340: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0350: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0360: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0370: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0380: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0390: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0400: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0410: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0420: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0430: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0440: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0450: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0460: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0470: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0480: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0490: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0500: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0510: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0520: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0530: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0540: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0550: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0560: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0570: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0580: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0590: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0600: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0610: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0620: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0630: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0640: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0650: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0660: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0670: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0680: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0690: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0700: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0710: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0720: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0730: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0740: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0750: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0760: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0770: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0780: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0790: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 2F1C 018B 0183 0191 1950 2FC3 0190 37E8
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 026A 3FFF 3FFF 32FF 3FFF 3FFF 3FFF 3FFF 3FFF 1F5D
Writing to memory...
Vpp initial: 7.6        PWM: 10
Vpp write mode: 11.2    PWM: 43
Vpp after writing: 11.1
Vpp off: 5.5
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 01:54:31 pm
Hi,

So this looks indeed like part of the OTP_ID. You can find the defines for OTP_ID in the IC specific files in "INC_PDK" folder of the IDE:
              OTP_ID     DATA from IC after command phase:

PMC150:    0B80
PMS150:    0B80
PMS150B:  1E01
PMS150C:  2A16     -> A16 (OK)

PMS154:    2A06
PMS154B:  2C06
PMS154C:  2C06     -> E06 (maybe include file is wrong or the read was not correct)
PFS154:     2AA1     -> AA1 (OK)


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 02:03:46 pm
Curiously a lot of memory cells were already written on the fresh device. See dump below. I only wrote to 0x20-0x27. So even at 0x00 there was a prior value programmed. Ideas anyone?

This looks like the factory testing routine. Might only be present in PMS devices (tested) compared to PMC devices (non tested). PADAUK says PMS devices = "higher yield" in production ... of course if they already check for bad ICs ;), PMC = "better value" (price cheaper since no factory test and you might get several bad ICs)

First instruction is a GOTO to the end of program area where a simple program is stored. I analyzed this program already: https://github.com/free-pdk/fppa-pdk-documentation/blob/master/SpecialCodeFoundInPMS154B.txt
Basically it is an endless loop mirroring the input of PA.5 inverted on PA4,PA.3 and PA.2 ==> WRITER could detect presence of good IC by setting PA.5 High/Low and checking if PA.4,PA.3,PA.2 output inverted signal (we saw this as continuous small spikes from time to time when WRITER is idle)

Later when you program a user program a NOP is placed at first instruction (NOP = all bits 0, like this you can overwrite the old value). The start of the real user program will be at next instruction (I saw this when I dumped a programed 154C).

The last 8 program words are documented partially by PADAUK and some more infos I wrote down here: https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 10, 2019, 02:22:15 pm
Curiously a lot of memory cells were already written on the fresh device. See dump below. I only wrote to 0x20-0x27. So even at 0x00 there was a prior value programmed. Ideas anyone?

This looks like the factory testing routine. Might only be present in PMS devices (tested) compared to PMC devices (non tested). PADAUK says PMS devices = "higher yield" in production ... of course if they already check for bad ICs ;), PMC = "better value" (price cheaper since no factory test and you might get several bad ICs)

First instruction is a GOTO to the end of program area where a simple program is stored. I analyzed this program already: https://github.com/free-pdk/fppa-pdk-documentation/blob/master/SpecialCodeFoundInPMS154B.txt
Basically it is an endless loop mirroring the input of PA.5 inverted on PA4,PA.3 and PA.2 ==> WRITER could detect presence of good IC by setting PA.5 High/Low and checking if PA.4,PA.3,PA.2 output inverted signal (we saw this as continuous small spikes from time to time when WRITER is idle)

Later when you program a user program a NOP is placed at first instruction (NOP = all bits 0, like this you can overwrite the old value). The start of the real user program will be at next instruction (I saw this when I dumped a programed 154C).

JS
Nop being all zeros seems like a nice way to give an OTP part a couple extra lives. Embedding relocation in the programmer code would be awesome.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 03:45:58 pm
Ok, PFC154 works now as well: Read/Erase/Write

- A major confusion for me was that there was an additional clock cycle after each read operation. JS, I think you were confused by the same issue. This seems to be a bus reversal cycle to give the slave time to release the data pin.
- The leading zero is missing from the write sequence compared to PMC150.
- Data is 14 bit, Adress 13. Pagesize is 4.
- Used the erase sequence that JS described in an earlier port. The only difference is that I ramped VPP only after the initilization sequence.

There is still some issue that requires memory positions to be written more than once. You can see this phenomon in the dump.  0x20 was written once, 0x24 twice, 0x28 thrice and 0x2c four times. The pattern should be "0x1a5a 000n 0000 0000", where n is the number of writes. As you can see it takes between three and four writes to reliably write that position. It is quite possible that this can be removed by increasing VDD. Therefore the analog logs by Frank will be very valuable.

Interestingly this behavior gets worse when writing at a higher Vpp.

I have observed a similar phenomon in the PMC150C but not in the PMS154.

Code: [Select]
Initializing...
DeviceID: AA1   Vpp Standby: 5.3 V
DeviceID is match to: PFC154
Dumping memory...
Vpp read mode: 7.7 V
0000: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0010: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0020: 1FFF 0FFF 0FFF 0FFF 1FFA 0182 05E0 0E80 1A5A 0003 0000 0000 1A5A 0004 0000 0000
0030: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0040: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0050: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0060: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0070: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0080: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0090: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0100: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0110: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0120: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0130: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0140: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0150: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0160: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0170: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0180: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0190: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0200: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0210: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0220: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0230: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0240: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0250: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0260: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0270: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0280: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0290: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0300: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0310: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0320: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0330: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0340: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0350: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0360: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0370: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0380: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0390: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0400: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0410: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0420: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0430: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0440: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0450: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0460: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0470: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0480: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0490: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0500: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0510: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0520: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0530: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0540: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0550: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0560: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0570: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0580: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0590: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0600: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0610: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0620: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0630: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0640: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0650: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0660: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0670: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0680: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0690: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0700: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0710: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0720: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0730: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0740: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0750: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0760: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0770: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0780: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0790: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 0282 025A 1FFE
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
Erasing device...
Erase init response: 0AA1
Vpp initial: 7.6 V      PWM: 9
Vpp erase mode: 8.8 V   PWM: 15
Vpp after erase: 8.9 V  PWM: 15
Writing to memory...
Vpp initial: 7.8 V      PWM: 10
Vpp write mode: 8.5 V   PWM: 15
Vpp after writing: 8.5 V
Vpp off: 4.5 V
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 03:48:56 pm
Hi,

So this looks indeed like part of the OTP_ID. You can find the defines for OTP_ID in the IC specific files in "INC_PDK" folder of the IDE:
              OTP_ID     DATA from IC after command phase:

PMC150:    0B80
PMS150:    0B80
PMS150B:  1E01
PMS150C:  2A16     -> A16 (OK)

PMS154:    2A06
PMS154B:  2C06
PMS154C:  2C06     -> E06 (maybe include file is wrong or the read was not correct)
PFS154:     2AA1     -> AA1 (OK)

Exellent find! The pieces of the puzzle are coming together now. :)

The mismatch between C06 and E06 is strange. The deviating bit is in the middle of the sequence, so it does not seem too likely that it glitched or flipped.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 03:56:54 pm
Ahaha, it's a bug in the chip. When I change words 3 and 4 to 0x3fff, all information is written in the first iteration. Probably there is some kind of internal issue when too many bits have to be written at once.
This explains why only two of four words are written at the same time in the official programmer.


Code: [Select]
Initializing...
DeviceID: AA1   Vpp Standby: 5.3 V
DeviceID is match to: PFC154
Dumping memory...
Vpp read mode: 7.7 V
0000: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0010: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0020: 1A5A 0001 3FFF 3FFF 1A5A 0002 3FFF 3FFF 1A5A 0003 3FFF 3FFF 1A5A 0004 3FFF 3FFF
0030: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0040: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0050: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0060: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0070: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0080: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0090: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
00F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0100: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0110: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0120: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0130: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0140: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0150: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0160: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0170: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0180: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0190: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
01F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0200: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0210: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0220: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0230: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0240: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0250: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0260: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0270: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0280: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0290: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
02F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0300: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0310: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0320: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0330: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0340: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0350: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0360: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0370: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0380: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0390: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
03F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0400: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0410: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0420: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0430: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0440: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0450: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0460: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0470: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0480: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0490: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
04F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0500: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0510: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0520: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0530: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0540: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0550: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0560: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0570: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0580: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0590: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
05F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0600: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0610: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0620: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0630: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0640: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0650: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0660: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0670: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0680: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0690: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
06F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0700: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0710: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0720: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0730: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0740: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0750: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0760: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0770: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0780: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
0790: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07A0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07B0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07C0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07D0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 0282 025A 1FFE
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
Erasing device...
Erase init response: 0AA1
Vpp initial: 7.9 V      PWM: 10
Vpp erase mode: 8.7 V   PWM: 14
Vpp after erase: 8.7 V  PWM: 14
Writing to memory...
Vpp initial: 7.7 V      PWM: 10
Vpp write mode: 8.7 V   PWM: 17
Vpp after writing: 9.0 V
Vpp off: 4.6 V
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 10, 2019, 04:12:30 pm
Nop being all zeros seems like a nice way to give an OTP part a couple extra lives. Embedding relocation in the programmer code would be awesome.
Actually the IDE has some support for it. See the file PADAUK_Tool/0.84/Help/CHS/MultPro.html . Unfortunately only available in Chinese, but the translation with Chrome is fairly good. It describes how to use .dc -1/0, .virtual and .checksum to burn an OTP IC virtually multiple times.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 04:32:37 pm
Ahaha, it's a bug in the chip. When I change words 3 and 4 to 0x3fff, all information is written in the first iteration. Probably there is some kind of internal issue when too many bits have to be written at once.
This explains why only two of four words are written at the same time in the official programmer.

The captures from writing PFS154 did not show that. The flash was written in one big go without writing some pages multiple times.

JS

BTW: "DeviceID is match to: PFC154" ==> should be PF*S*154 ;-)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 04:34:46 pm
Hi,

So this looks indeed like part of the OTP_ID. You can find the defines for OTP_ID in the IC specific files in "INC_PDK" folder of the IDE:
              OTP_ID     DATA from IC after command phase:

PMC150:    0B80
PMS150:    0B80
PMS150B:  1E01
PMS150C:  2A16     -> A16 (OK)

PMS154:    2A06
PMS154B:  2C06
PMS154C:  2C06     -> E06 (maybe include file is wrong or the read was not correct)
PFS154:     2AA1     -> AA1 (OK)

Exellent find! The pieces of the puzzle are coming together now. :)

The mismatch between C06 and E06 is strange. The deviating bit is in the middle of the sequence, so it does not seem too likely that it glitched or flipped.

It's also strange that the "B" part has same OTP-ID as the "C" part. On several other processors "B" and "C" always have different OTP-IDs. SO maybe a bug in PDK include file...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 04:53:09 pm
Ahaha, it's a bug in the chip. When I change words 3 and 4 to 0x3fff, all information is written in the first iteration. Probably there is some kind of internal issue when too many bits have to be written at once.
This explains why only two of four words are written at the same time in the official programmer.

The captures from writing PFS154 did not show that. The flash was written in one big go without writing some pages multiple times.

JS

BTW: "DeviceID is match to: PFC154" ==> should be PF*S*154 ;-)

I thought this came up somewhere up in the thread? Well anyways. The issue with not being able to write many zeros at the same time could be a current limitation. The embedded MTP memory is probably written with hot carrier injection or another mechanism that requires a lot of current. The total current consumption during writing depends on the numbers of zeros written. I should maybe try to use a transistor to control VDD instrad of a GPIO...

Indeed, chnaged to PFS.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 05:12:19 pm
I thought this came up somewhere up in the thread? Well anyways. The issue with not being able to write many zeros at the same time could be a current limitation. The embedded MTP memory is probably written with hot carrier injection or another mechanism that requires a lot of current. The total current consumption during writing depends on the numbers of zeros written. I should maybe try to use a transistor to control VDD instrad of a GPIO...

Interesting...

I was able to READ/ERASE with VDD coming from STM32 (3.3V, smallish current) and it worked nice. However writing only sometimes changed some bits.
When I added a transistor to switch VDD (basically wiring resistor to VDD supplied from external PSU and using mosfet to pull it to ground... I know but I had it handy) situation got worse.
I could not write anything anymore. However READ and ERASE still worked.

My experiments with PFS154:
* any VPP 5.7 - 12V and any VDD 2.4 - 7V READ/ERASE works
* WRITE worked only  (a little bit) when VDD was connected to MCU (3.3V), it also stopped working with 3.3V when using the transistor.

So maybe my current limiting resistor needs to be changed. Can't wait to try later today :-)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 05:25:05 pm
The datasheet actually states that VDD can draw up to 20mA during programming. Could already be a bit too much.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 10, 2019, 10:55:46 pm
I thought this came up somewhere up in the thread? Well anyways. The issue with not being able to write many zeros at the same time could be a current limitation. The embedded MTP memory is probably written with hot carrier injection or another mechanism that requires a lot of current. The total current consumption during writing depends on the numbers of zeros written. I should maybe try to use a transistor to control VDD instrad of a GPIO...

Interesting...

I was able to READ/ERASE with VDD coming from STM32 (3.3V, smallish current) and it worked nice. However writing only sometimes changed some bits.
When I added a transistor to switch VDD (basically wiring resistor to VDD supplied from external PSU and using mosfet to pull it to ground... I know but I had it handy) situation got worse.
I could not write anything anymore. However READ and ERASE still worked.

My experiments with PFS154:
* any VPP 5.7 - 12V and any VDD 2.4 - 7V READ/ERASE works
* WRITE worked only  (a little bit) when VDD was connected to MCU (3.3V), it also stopped working with 3.3V when using the transistor.

So maybe my current limiting resistor needs to be changed. Can't wait to try later today :-)

JS

THIS DID THE TRICK!!! Correct VDD voltage + current is essential.  :) :D ;D

When I set VDD to exact 5.8V for PFS154 i could write the complete IC in one go.
<5.7 V only some bits wrong during PAGE WRITE all 0
<5.4 V several bits wrong during PAGE WRITE all 0
<=5 V only some bits changed during PAGE WRITE all with 0

BTW: It is enough to setup VDD + VPP only once. There is no need to change it during a READ/ERASE/WRITE operation.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2019, 11:06:29 pm
Great! Very nice finding. That means that very accurate VDD control is needed - or you need to write only a limited number of zeros at the same time.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 11, 2019, 12:06:26 am
After some discussion with a friend and looking on oscilloscope we found that my VDD broke down frequently (e.g. once per bit during read).

So maybe not so sensitive at all, but a capacitor is required to stabilize VDD.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 11, 2019, 07:34:16 am
Adding a stabilizing cap unfortunately did not solve the issue for my programmer. Neither did using a transistor to switch VDD. So it really seems to be related to supply voltage as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on January 11, 2019, 01:03:33 pm
I put 1ms delay after sending address and it fixed my double write problem. (PFS154-08)
I'm using 12V VPP and 5V VCC.

(https://images89.fotosik.pl/103/a130b4c3ca0b767fm.jpg) (https://images89.fotosik.pl/103/a130b4c3ca0b767f.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on January 12, 2019, 11:31:53 am
I think it could be very helpful to take an analog log of the PFS154 writes sequence. Most likely it will also be possible to deduce the write direction from the analog voltages.
Frank, do you think you have a chance to do this? If you don't have any PFS154 I could send some to you.

Thanks, I got the ICs. Here (http://www.frank-buss.de/tmp/dump-pfs154.zip) is a dump of the PFS154. I added a lot of 0x00 and 0xff to see if the programmer does something special for long sequences. The test project with source code and PDK file is included. This is programming an already programmed chip with the same data, but in the display I could read an erase step, so I guess it is the same for an empty chip. But I can do another test with an empty chip, if necessary.

Signals:

CH1 = PA3
CH2 = PA5
CH3 = PA6
CH4 = VDD

Still a lot of crosstalk. My scope shows a better signal. But I think I can reduce this a bit with a better decoupling of the reference voltages and better shielding of the test cables.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 12, 2019, 02:58:42 pm
I think it could be very helpful to take an analog log of the PFS154 writes sequence. Most likely it will also be possible to deduce the write direction from the analog voltages.
Frank, do you think you have a chance to do this? If you don't have any PFS154 I could send some to you.

Thanks, I got the ICs. Here (http://www.frank-buss.de/tmp/dump-pfs154.zip) is a dump of the PFS154. I added a lot of 0x00 and 0xff to see if the programmer does something special for long sequences. The test project with source code and PDK file is included. This is programming an already programmed chip with the same data, but in the display I could read an erase step, so I guess it is the same for an empty chip. But I can do another test with an empty chip, if necessary.

Signals:

CH1 = PA3
CH2 = PA5
CH3 = PA6
CH4 = VDD

Still a lot of crosstalk. My scope shows a better signal. But I think I can reduce this a bit with a better decoupling of the reference voltages and better shielding of the test cables.

Thanks a lot! Looking at the data right now. As I'd hoped for, it is possible to identify the data directon from voltages and also slew rates. It seems that most assumptions about the protocol are confirmed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 12, 2019, 08:06:56 pm
There was a  bit of progress on the software side. The compiler is now mostly working (i.e. except for a few corner cases it should just accept valid ISO C17 code and generate correct asm for it), and the generated asm looks okayish, though there is further potential for optimization.

I've written a "Hello, world!" for the PFS154 (https://github.com/free-pdk/sdcc-pdk-code-examples/tree/master/hello-pfs154). The asm generated by SDCC for it looks correct, but I didn't really check the binary code yet (and the assembler is still quite new).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 03:09:50 am
There was a  bit of progress on the software side. The compiler is now mostly working (i.e. except for a few corner cases it should just accept valid ISO C17 code and generate correct asm for it), and the generated asm looks okayish, though there is further potential for optimization.

I've written a "Hello, world!" for the PFS154 (https://github.com/free-pdk/sdcc-pdk-code-examples/tree/master/hello-pfs154). The asm generated by SDCC for it looks correct, but I didn't really check the binary code yet (and the assembler is still quite new).

Philipp

Very nice! I compiled SDCC from your pdk branch and compiled this example. It seems that main code and the initiliaztion code are both relocated to zero? Is that still a bug or is an additional linker-file required?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 13, 2019, 09:53:19 am
Very nice! I compiled SDCC from your pdk branch and compiled this example. It seems that main code and the initiliaztion code are both relocated to zero? Is that still a bug or is an additional linker-file required?

Kind of both: One could use a linker file (or the --code-loc option), but the default for --code-loc needs to be changed, so it just works for the common case. However, there also are a few other linker / compiler-linker interface issues that need to be fixed.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 10:24:58 am
Kind of both: One could use a linker file (or the --code-loc option), but the default for --code-loc needs to be changed, so it just works for the common case. However, there also are a few other linker / compiler-linker interface issues that need to be fixed.

Philipp

Is there any easy workaround? I am currently looking for a way to generate a binary to test programming with a real example, preferrably as intel hex. I made a small blinky example (attached). Apart from the relocation issues, it seems  to look fine. Otherwise I'll try to use the assembler directly.

I'd prefer not to use the official* Padauk IDE right now for several reasons:
- The tools to decode pdk files from "freepdk" do not compile. (who is maintaining this, btw. I added an issue)
- I would like omit the oscillator calibration code for now as this only adds to complexity to the programmer.
- Out of principle, to avoid IP contamination.

*edit

Code: [Select]
/*
Blinky on PA.0
*/


#include <stdbool.h>
#include <stdio.h>

volatile int counter;

__sfr __at(0x03) clkmd;
__sfr __at(0x04) inten;
__sfr __at(0x05) intrq;
__sfr __at(0x10) pa;
__sfr __at(0x11) pac;
__sfr __at(0x1c) tm2c;
__sfr __at(0x17) tm2s;
__sfr __at(0x09) tm2b;

unsigned char _sdcc_external_startup(void)
{
clkmd = 0x34; // Use IHRC / 2 = 8 Mhz for system clock
clkmd = 0x30; // Disable ILRC, watchdog

return 0; // perform normal initialization
}

void main(void)
{
pac = 0x01; // PA.0=output

for (;;) {
counter=30000;
while (--counter);
pa=0x00;

counter=30000;
while (--counter);
pa=0x01;
}
}

Code: [Select]
:200002000113002F800B002F002880171830002F800300120830000C01286A006B00820151
:020002000030CC
:020000000C30C2
:20000400342F830B302F830B7A007A00012F910B302F800B752F810B80128110800F810EE3
:1C002400002A1830002F900B80128110800F810E002A2830012F900B10307A003C
:00000001FF
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 03:57:21 pm
A general issue with SDASPDK: It seems all adress calculation for the instruction memory are based on bytes, not words. Therefore branch targets are off by a factor of two. Or am I missing something?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 13, 2019, 04:02:03 pm
Kind of both: One could use a linker file (or the --code-loc option), but the default for --code-loc needs to be changed, so it just works for the common case. However, there also are a few other linker / compiler-linker interface issues that need to be fixed.

Philipp

Is there any easy workaround?

Compiling with --code-loc 0x0011 or so might help. Worst case one could manually fix the jump targets in the binary. But I don't consider the sdcc-based toolchain ready yet. Work on linker integration has just started. There are probably bugs in the compiler and assembler, many of which will probably not be found before regression testing on the yet-to-be-written-and-ntegrated uCsim-based simulator is in place.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 13, 2019, 05:40:57 pm
I'd prefer not to use the padauk tools right now for several reasons:
- The tools to decode pdk files from "freepdk" do not compile.
This is just not correct. The tools do compile fine for me.

(who is maintaining this, btw. I added an issue)
Read this thread and you know who are maintainers.
Also your question looks like you did understood open source development wrong. If something is not working for you it is not the time to cry for a maintainer to help and and fix your problems.
It is much better if you try at least a little bit to investigate yourself and then come up with possible solutions.
The issue is still open since a proper problem / bug report needs some good information which you did not include. Basically an "It is not working on my msys2 (windows)" or "also not working on recent Mint" without any version information, processor architecture, compiler version, ..." is not helpful. I gave you some examples in the issue on github what a good bug report should contain...

- I would like omit the oscillator calibration code for now as this only adds to complexity in the programmer.

Again, read this thread any you know how to do it.

- Out of principle, to avoid IP contamination.

This is the most funny thing you ever posted here. You want to avoid IP contamination?? How do you plan to "avoid" the IP-Core running in the PADAUK IC?
If this really is your concern then for sure you should go with RISC-V.


So dear "tim_" / "cpldcpu" please stop speaking bad about others work or things which you did not "create" yourself.

Isn't it enough that you suggest in your german super forum that most of the community work from this thread looks like you been the one who did it / who found it?

Do you really need to sabotage other projects now?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 06:00:53 pm
Guys, this is getting too much for me. JS, you may need to think twice before writing angry responses on the internet.

Regarding the issue with compiling the toolchain: I put into the issue on github what I know. I tried two different toolchains on two operating systems and got the same issue. The root cause is not apparent to me now, that's why I opened an issue instead of a pull request. OSS is not about "do everything on your own", that's just very inefficient.

Regarding IP contamination, you may want to read the link about "clean room implementation" that I posted earlier. I agree that it is unlikely to run into issues with Padauk, but in the end it should be my own choice to follow clean processes.

Btw, got a blinky working now on the PFS154 with the OSS toolchain (SDASPDK), and an arduino based programmer. Still extremely hacky.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 13, 2019, 06:03:13 pm
- Out of principle, to avoid IP contamination.

This is the most funny thing you ever posted here. You want to avoid IP contamination?? How do you plan to "avoid" the IP-Core running in the PADAUK IC?
If this really is your concern then for sure you should go with RISC-V.
While I consider free hardware to be a good thing, there is still a difference. Richard Stallman draws the line between stuff that is supposed to be changed by the user (updateable programs, firmware, FPGA configuration) and and stuff that isn't (e.g. a ROM in a device), which seems to make sense to me.

So a position of not being willing to use non-free software can make sense.

And there is indeed some risk of "IP contamination": AFAIK, Mini-C adds some of its own code into the resulting program. Many compilers,like GCC or SDCC have a "linker exception" in the license for their library, so the resulting program is not affected by the library license. I din't notice something similar in Mini-C yet (but maybe I just didn't check closely enough). On the other hand, maybe whatever Mini-C adds is unsubstantial enough to not affect the license of the wholeprogram. But that might depend on jurisdiction.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 06:08:39 pm
Compiling with --code-loc 0x0011 or so might help. Worst case one could manually fix the jump targets in the binary. But I don't consider the sdcc-based toolchain ready yet. Work on linker integration has just started. There are probably bugs in the compiler and assembler, many of which will probably not be found before regression testing on the yet-to-be-written-and-ntegrated uCsim-based simulator is in place.

Philipp

There were still some remaining relocation conflicts. What I did in the end:

- I used the *.asm file as a basis for an assembler version to fix the relocation issues.
- For MOVs to the I/O region, the assembler generated the opcode for MOV to SRAM. I fixed it manually in the binary.

Everything works now and I got a flashing LED connected to a PFS154.  ;D

Code: [Select]
;--------------------------------------------------------
; Blinky for Padauk PFS154C
; Based on asm code generated from blinky.c by SDD
;
; File Created by SDCC : free open source ANSI-C Compiler
; Version 3.8.6 #10883 (Linux)
;--------------------------------------------------------
.module blinky
.optsdcc -mpdk14

;--------------------------------------------------------
; Public variables in this module
;--------------------------------------------------------
.globl _main
.globl _tm2b
.globl _tm2s
.globl _tm2c
.globl _pac
.globl _pa
.globl _intrq
.globl _inten
.globl _clkmd
.globl _counter
;--------------------------------------------------------
; special function registers
;--------------------------------------------------------
.area RSEG (ABS)
.org 0x0000
_clkmd = 0x0003
_inten = 0x0004
_intrq = 0x0005
_pa = 0x0010
_pac = 0x0011
_tm2c = 0x001c
_tm2s = 0x0017
_tm2b = 0x0009
;--------------------------------------------------------
; ram data
;--------------------------------------------------------
.area DATA
_counter::
.ds 2
;--------------------------------------------------------
; overlayable items in ram
;--------------------------------------------------------
;--------------------------------------------------------
; Stack segment in internal ram
;--------------------------------------------------------
.area SSEG
__start__stack:
.ds 1

;--------------------------------------------------------
; absolute external ram data
;--------------------------------------------------------
.area DABS (ABS)
;--------------------------------------------------------
; interrupt vector
;--------------------------------------------------------
.area HOME
__interrupt_vect:
;--------------------------------------------------------
; global & static initialisations
;--------------------------------------------------------
.area HOME
.area GSINIT
.area GSFINAL
.area GSINIT
.area PREG (ABS)
; .area CODE
.org 0x00
__sdcc_program_startup:
goto _main
; return from main will return to caller
;--------------------------------------------------------
; code
;--------------------------------------------------------
.org 0x10
; -----------------------------------------
; function main
; -----------------------------------------
_main:
mov a, #0x78
mov _clkmd, a
mov a, #0x01
mov _pac, a
00108$:
mov a, #0x30
mov _counter+0, a
mov a, #0x75
mov _counter+1, a
; blinky.c: 35: while (--counter);
00101$:
dec _counter+0
subc _counter+1
mov a, _counter+0
or a, _counter+1
ceqsn a, #0x00
goto 00101$
; blinky.c: 36: pa=0x00;
mov a, #0x00
mov _pa, a
; blinky.c: 38: counter=30000;
mov a, #0x30
mov _counter+0, a
mov a, #0x75
mov _counter+1, a
; blinky.c: 39: while (--counter);
00104$:
dec _counter+0
subc _counter+1
mov a, _counter+0
or a, _counter+1
ceqsn a, #0x00
goto 00104$
; blinky.c: 40: pa=0x01;
mov a, #0x01
mov _pa, a
goto 00108$
00110$:
; blinky.c: 42: }
ret




Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 13, 2019, 06:14:27 pm
Guys, this is getting too much for me. JS, you may need to think twice before writing angry responses on the internet.

Regarding the issue with compiling the toolchain: I put into the issue on github what I know. I tried two different toolchains on two operating systems and got the same issue. The root cause is not apparent to me now, that's why I opened an issue instead of a pull request. OSS is not about "do everything on your own", that's just very inefficient.

Regarding IP contamination, you may want to read the link about "clean room implementation" that I posted earlier. I agree that it is unlikely to run into issues with Padauk, but in the end it should be my own choice to follow clean processes.

Btw, got a blinky working now on the PFS154 with the OSS toolchain (SDASPDK), and an arduino based programmer. Still extremely hacky.

So why do you think I get angry?

>Regarding the issue with compiling the toolchain: I put into the issue on github what I know. I tried two different toolchains on two operating systems and got the same issue.
=> Exact like I wrote, without proper version information of your problem it is not helpful at all. It's like saying I tried to kick the ball in the goal 2 times but it did not work, so the ball must be broken.

>The root cause is not apparent to me now, that's why I opened an issue instead of a pull request.

>OSS is not about "do everything on your own", that's just very inefficient.
=> I said you should a least TRY to solve the problem. I did NOT say you should "do everything on your own".

>Btw, got a blinky working now on the PFS154 with the OSS toolchain (SDASPDK), and an arduino based programmer. Still extremely hacky.
=> Aha... ""you"" got "a" blinky working (again you comfortably forgot to mention that the blinky was based on spth's port of the blinky was based on the free-pdk sample, spth cleary mentioned it.

JS

EDIT: Just saw that you posted "YOUR" blinky... just as expected. Waiting for your posting in german forum claiming YOU just did the first blinky for PFS154 only using open source for compilation and flashing based on your hard work.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 06:18:33 pm
And there is indeed some risk of "IP contamination": AFAIK, Mini-C adds some of its own code into the resulting program. Many compilers,like GCC or SDCC have a "linker exception" in the license for their library, so the resulting program is not affected by the library license. I din't notice something similar in Mini-C yet (but maybe I just didn't check closely enough). On the other hand, maybe whatever Mini-C adds is unsubstantial enough to not affect the license of the wholeprogram. But that might depend on jurisdiction.

Philipp

Indeed. It is possible that Padauk sees the process of adjusting the clock in the programmer as their IP or maybe even has patented it. In that case it would be better to completey omit this process or come up with a clean room implementation that is not based on reverse engineering code.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 13, 2019, 06:24:16 pm
JS, you need to chill out.

I will take a break from this forum for now.

And you should at least try to FULLY read and understand what I said.

Just an example:

I'd prefer not to use the bilnky from tim_ right now for several reasons:
- The source from "tim_" do not compile. (who is maintaining this, btw. I should add an issue)
- I would like to omit the source parts from blinky taken from others without giving notice
- Out of principle, to avoid LICENSE contamination.

Would this kind of words make you happy?

JS

EDIT:

Some more examples?:

here you mention that the binary format was deciphered: https://www.mikrocontroller.net/topic/461002#5616184 (https://www.mikrocontroller.net/topic/461002#5616184)
one post later(10. Nov) it looks like YOU found some valuable information / links (and as usual, you comfortably "forgot" where you found the information) => (07. Nov): https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1946455/#msg1946455 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1946455/#msg1946455)

(7 Jan.) you created a posting on your german forum announcing that there was progress deciphering the programing protocol by linking just to the data capture and your analysis (and as usual you comfortably "forgot" to mention the work of all people from this thread here): https://www.mikrocontroller.net/topic/461002#5685419 (https://www.mikrocontroller.net/topic/461002#5685419)

...

Do you see the pattern? So maybe some people might get angry?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 13, 2019, 06:41:30 pm
I'd prefer not to use the bilnky from tim_ right now for several reasons:

Oh I see the misunderstanding: With "Padauk-tools" I referred to the tools by the company Padauk. I was only referencing the "Free-pdk" tools, because I would need them to decode the PDK file.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 15, 2019, 10:23:44 pm
A general issue with SDASPDK: It seems all adress calculation for the instruction memory are based on bytes, not words. Therefore branch targets are off by a factor of two. Or am I missing something?

The assembler was contributed by Nicolas Lesser. I just merged a patch by him that fixes this issue.

There are a few additional examples at https://github.com/free-pdk/sdcc-pdk-code-examples now; they seem to compile and assemble fine, but I didn't try them on simulator / hardware yet (I've just designed some minimal evaluation boards).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 03:08:40 pm
I was thinking of creating calibration code for Internal Highspeed RC (IHRC) and came up with the following minimal code:


_STARTUP:
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration
      MOV A,0xFF                        ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
      MOV IHRCR, A                    ;set the calibration value

      ;set SP, init .BSS, init .DATA, ...

      ;user code here

;----------------------------------------------------------------

.RAMADR 0
      BYTE TMP

.ROMADR   0x7D0

_CALIBRATION:
      CLEAR TMP                  ;set TMP to 0
_CAL_NEXT_STEP:
      MOV A,0x10                 ;PA.5 as output, rest as input  => this pin should exist on all devices, same as RESET/ICVPP pin
      MOV PAC,A
_CAL_WAIT_HOST:
      T1SN PA.6                  ;read bit from PA.6 (measurement start?) => this pin should exist on all devices, same as ICPDA pin
      GOTO _CAL_WAIT_HOST
_CAL_TOGGLE_LOOP:
      XOR PA,A                   ;invert output of PA.5
      T0SN PA.6                  ;read bit from PA.6 (measurment done?)
      GOTO _CAL_TOGGLE_LOOP
      INC TMP                    ;increment TMP value (will run from 0 - 255, increment by 1 with each measurement done single)
      MOV A,TMP                  ;read the current TMP value
      MOV IHRCR, A               ;write current TMP value to IHRCR tuning register
      GOTO _CAL_NEXT_STEP        ;jump to next calibration step

;------------------------------------------------------------------------
;assembly output (14 bit) of the calibration (12 instructions)

0x07d0:   0x1300    CLEAR [0x00]
0x07d1:   0x2f10    MOV A, 0x10
0x07d2:   0x0191    MOV IO(0x11), A  ;PAC
0x07d3:   0x1b90    T1SN IO(0x10).6  ;PA.6
0x07d4:   0x37d3    GOTO 0x7D3
0x07d5:   0x00d0    XOR IO(0x10), A  ;PA
0x07d6:   0x1990    T0SN IO(0x10).6  ;PA.6
0x07d7:   0x37d5    GOTO 0x7D5
0x07d8:   0x1200    INCM [0x00]
0x07d9:   0x0f80    MOV A, [0x00]
0x07da:   0x018b    MOV IO(0x0B), A  ;IHRCR
0x07db:   0x37d1    GOTO 0x7D1


STARTUP CODE:
1st instrucrtion is a GOTO to the calibration code, this GOTO will be changed to a NOP after calibration was done
-> this is faster and more compact than PADAUK code since no stack setup is required for the CALL and CALL+RET wastes more cycles than overwrite GOTO with NOP (actually the calibration never need to return since we can reset/unpower the IC to leave this mode)
2nd instruction is a MOV A,0xFF which can be overwritten to anything like MOV A,0x.. later (this will receive the calibration value)
-> again faster
3rd instructions sets the IHRCR tuning register value
...

CALIBRATION CODE:
PA.5 is used as output from IC which toggles on/off in a tight loop => output max is up to 9 MHz which can be captured and counted in hardware on host MCU easily (e.g. TIM on STM32); measurement of how many toggle in specific time period
PA.6 is used as input to IC to signal measurement start and measurement done, after each measurement done the value of IHRCR is incremented and the next measurement can start
-> this is slower than PADAUK since we can not go up/down (+1/-1) we have to cycle over all 256 values of the byte instead, but it is a lot more compact, and calibration does not need to be so fast...


So now asking you for creative ideas to make it even more compact ( < 3 + 12 instructions )

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: j7b on January 16, 2019, 04:11:11 pm
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration

How would one overwrite or otherwise change instructions?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 16, 2019, 04:13:04 pm
XOR PA,A is only supported by few devices.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 16, 2019, 04:14:54 pm
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration

How would one overwrite or otherwise change instructions?

A nop is all-zero. When writing PROM, a 1 can be changed to 0 any time (a few years ago, in a different device, a bug was discovered after PROMs had been programmed - so I had to come up with a patch that only flips 1 bits to 0).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: j7b on January 16, 2019, 04:58:51 pm
A nop is all-zero. When writing PROM, a 1 can be changed to 0 any time (a few years ago, in a different device, a bug was discovered after PROMs had been programmed - so I had to come up with a patch that only flips 1 bits to 0).

You're changing an OTP device's ROM via software after calibration?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 16, 2019, 05:49:42 pm
A nop is all-zero. When writing PROM, a 1 can be changed to 0 any time (a few years ago, in a different device, a bug was discovered after PROMs had been programmed - so I had to come up with a patch that only flips 1 bits to 0).

You're changing an OTP device's ROM via software after calibration?

The calibration routine runs on the device. The programmer calculates the correct calculation value while it is executed. Then the programmer writes final program and calibration value onto the device.
So the initial jump to the calibration routine gets overwritten by a nop. The final user program follows the nop. The calibration routine is somewhere near the end of the ROM space.

AFAIK, some devices even come with a factory-self-test routine (in the manual, there is a note about a part of the ROM being reserved for "system use", for details see earlier posts in this thread).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 16, 2019, 06:06:43 pm
OTP is like fuses, 0=blown, 1=intact. You can blow them anytime, but never restore them back.

You may also blow some fuses now and some at a later time.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 07:14:15 pm
XOR PA,A is only supported by few devices.

Philipp

Yes this is true. I think we will have different calibration routines for 13,14,15,16 bit devices.
For example on 16 bit devices we have the toggle instruction, so A register could be free completely, no memory needed some instructions saved...

hmmm... let's me think:

_CALIBRATION:
      MOV A,0                    ;maybe not needed since A might be 0 after reset?
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
_CAL_NEXT_STEP:
      MOV IHRCR, A               ;write current A value to IHRCR tuning register
_CAL_WAIT_HOST:
      T1SN PA.6                  ;read bit from PA.6 (measurement start?)
      GOTO _CAL_WAIT_HOST
_CAL_TOGGLE_LOOP:
      SET1 PA.5                  ;set output of PA.5 to 1
      SET0 PA.5                  ;set output of PA.5 to 0
      T0SN PA.6                  ;read bit from PA.6 (measurment done?)
      GOTO _CAL_TOGGLE_LOOP
      ADD A,1                    ;increment A (will run from 0 - 255, increment by 1 with each measurement done single)
      GOTO _CAL_NEXT_STEP        ;jump to next calibration step


1 instruction saved, not using the XOR IO anymore :)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 16, 2019, 07:31:48 pm
Maybe one could use SET1 and SET0 to toggle the clock? Then no memory write is needed. V1 needs the host to be really fast and issue a timed signal on PA6 to increment TMP. V2 will wait until PA6 is released again.

Edit: I see you were faster and already posted a version with SET0 and SET1 :)

Code: [Select]
_CALIBRATION_V1:
      SET1 PAC,5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, same as RESET/ICVPP pin
      MOV A,0
_CAL_MAIN_LOOP:
      T1SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      ADD  A,1
      SET1 PA,5                  ;output one clock cycle
      SET0 PA,5
      MOV IHRCR, A               ;write current A value to IHRCR tuning register
      GOTO _CAL_MAIN_LOOP     
     

_CALIBRATION_V2:
      SET1 PAC,5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, same as RESET/ICVPP pin
      MOV A,0
_CAL_MAIN_LOOP:
      T1SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      ADD  A,1
      SET1 PA,5                  ;output one clock cycle
      SET0 PA,5
      MOV IHRCR, A               ;write current A value to IHRCR tuning register
_CAL_WAIT
      T0SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      GOTO _CAL_MAIN_LOOP     
      GOTO _CAL_WAIT
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 08:59:11 pm
Maybe one could use SET1 and SET0 to toggle the clock? Then no memory write is needed. V1 needs the host to be really fast and issue a timed signal on PA6 to increment TMP. V2 will wait until PA6 is released again.

Edit: I see you were faster and already posted a version with SET0 and SET1 :)

Code: [Select]
_CALIBRATION_V1:
      SET1 PAC,5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, same as RESET/ICVPP pin
      MOV A,0
_CAL_MAIN_LOOP:
      T1SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      ADD  A,1
      SET1 PA,5                  ;output one clock cycle
      SET0 PA,5
      MOV IHRCR, A               ;write current A value to IHRCR tuning register
      GOTO _CAL_MAIN_LOOP     
     

_CALIBRATION_V2:
      SET1 PAC,5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, same as RESET/ICVPP pin
      MOV A,0
_CAL_MAIN_LOOP:
      T1SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      ADD  A,1
      SET1 PA,5                  ;output one clock cycle
      SET0 PA,5
      MOV IHRCR, A               ;write current A value to IHRCR tuning register
_CAL_WAIT
      T0SN PA.6                  ;read bit from PA.6, increment IHRCR when low. Needs to be low for only one clock cycle!
      GOTO _CAL_MAIN_LOOP     
      GOTO _CAL_WAIT

In your version you increment the tuning register with each clock output. This is way to fast to measure. The original version toggles the bit in a loop with same IHRCR value until host signals to change it.
EDIT: never mind, didn't see the SN instruction before the ADD  |O


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 09:27:09 pm
New idea:


_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration
     
      ;set SP, init .BSS, init .DATA, ...

      ;user code here

     
_CALIBRATION:
      MOV  A,0
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
_CAL_TOGGLE_LOOP:
      SET1 PA.5                  ;set output of PA.5 to 1
      SL A                       ;shit left A, set carry if msb was 1 before shift
      T1SN PA.6                  ;read bit from PA.6
      OR A,1                     ;set lowest bit (skipped when PA.6 is 0)
      SET0 PA.5                  ;set output of PA.5 to 0
      T0SN CF                    ;CF not set?
      GOTO _CAL_TOGGLE_LOOP
      GOTO _STARTUP_IHRCR


new tricks:
- we can jump around and reuse MOV IHRCR,A from startup code
- setup of A is now done via SPI like communication where IC is master and WRITER is slave:
   * PA.5 is clock (from IC)
   * PA.6 is MISO (data coming into IC)
   * whenever WRITER wants to setup a new IHRCR value it needs to send 9 bits with MSB set to 1, e.g. 0x153 => IHRCR will be set to 0x53
     (the 9th bit is detected by detecting an overflow in SL A (shift left instruction))
   * when WRITER wants to run the calibration loops it sends 0 all the time (SL A will never produce a carry)

=> 3 + 10 instructions now and we can set specific IHRCR value from host directly


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 16, 2019, 10:03:21 pm
In your version you increment the tuning register with each clock output. This is way to fast to measure. The original version toggles the bit in a loop with same IHRCR value until host signals to change it.

Well, there are two versions in the code, V1 and V2. For the first version, a timed signal is needed on the input. This could be done by using a D-flipflop or SPI slave. Maybe a bit too much effort to save two words of memory...

The second version is two more words and will wait for the external input to change again.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 16, 2019, 10:05:52 pm
New idea:


Looks great! I love the trick of starting at 0xff to reuse the initialization value. Also much better to control the calibration value from the outside. This would allow to verify the setting. Otherwise there is a risk of bricking the device if there is a glitch during programming.

If you use CF=0 instead of CF=1 to signify a transmission you may be able to remove the MOV A,0?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 10:20:16 pm
Looks great! I love the trick of starting at 0xff to reuse the initialization value. Also much better to control the calibration value from the outside. This would allow to verify the setting. Otherwise there is a risk of bricking the device if there is a glitch during programming.

If you use CF=0 instead of CF=1 to signify a transmission you may be able to remove the MOV A,0?

Hmm, I cant not see what you mean. I only see that the MOV A,0xFF is before the MOV IHRCR,A and can not be used to reset A. The reset is required after a byte was clocked in since A could still have 1/0 bits which could produce more carry flags at next shifts.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 16, 2019, 10:28:08 pm
Hmm, I cant not see what you mean. I only see that the MOV A,0xFF is before the MOV IHRCR,A and can not be used to reset A. The reset is required after a byte was clocked in since A could still have 1/0 bits which could produce more carry flags at next shifts.

Ah indeed, it's better to reset A. It would also be possible to shift out the current word, but that would result in a lot of intermediate clock setttings - probably too risky.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 16, 2019, 10:49:52 pm
Do we really need to fully send the value for IHRCR? Wouldn't it be sufficient if we always start with 0xFF and allow the programmer to decrease the value by 1 when setting PA.6 high for one cycle?

That way the programmer has still control over IHRCR, albeit a tad slower, but a few milliseconds don't matter during calibration. But you wouldn't need to reset A to 0 and you wouldn't need the SL. Or do I miss something?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 16, 2019, 11:35:47 pm
Do we really need to fully send the value for IHRCR?
This idea was a using less instructions and had the benefit of controlling the value.

Wouldn't it be sufficient if we always start with 0xFF and allow the programmer to decrease the value by 1 when setting PA.6 high for one cycle?
That way the programmer has still control over IHRCR, albeit a tad slower, but a few milliseconds don't matter during calibration. But you wouldn't need to reset A to 0 and you wouldn't need the SL. Or do I miss something?

There is a problem to know which cycle is the correct cycle to set PA.6 high for one cycle.
In order to be sure that it will trigger the single test instruction for PA.6 in the loop you must set the PA.6 high for all instructions in the loop -1 (or -2 cycles) you get from the non taken JUMP and setup of new IHRCR. This is a very hard to do timing, especially if you try to calibrate a chip clock drift (you have to assume that the clock on the Padauk IC is not working at correct speed... we just try to find a good value to let it work at the correct speed).

EDIT: Hmm, on the other hand we could use the SPI way and send a single bit (8 bit SPI sending 0x01)

So like "tim_" V1 mixed with reuse of startup code:

_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration
     
      ;set SP, init .BSS, init .DATA, ...

      ;user code here     


_CALIBRATION:
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
_CAL_TOGGLE_LOOP:
      SET1 PA.5                  ;set output of PA.5 to 1
      SET0 PA.5                  ;set output of PA.5 to 0
      T1SN PA.6                  ;read bit from PA.6
      GOTO _CAL_TOGGLE_LOOP
      ADD A,1                    ;increment A
      GOTO _STARTUP_IHRCR


now: 3 + 7 instructions ( not bad compared to the 73 instructions from PADAUK standard PFS154 calibration: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1982153/#msg1982153 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1982153/#msg1982153) )

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 17, 2019, 03:27:20 am
According to the PMS150C datasheet it boots with ILRC not IHRC. May need setting CLKMD before calibration.

To avoid strict timing requirements the loop can be rewritten to make it slower. In the code below it should be safe to change PA.6 any time PA.5 is low, and it should stay low a lot longer than high. On the programmer set a rising edge-triggered interrupt on PA.5, busy-wait until cleared, then change PA.6.

Also, accidentally shaved one instruction away. :-) At least if rewriting IHRCR and PAC with the same values has no side efects.

Code: [Select]
_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration

      ;user code here     


_CALIBRATION:
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
      SET1 PA.5                  ;set output of PA.5 to 1
      T0SN PA.6                  ;read bit from PA.6
      ADD A,1                    ;increment A
      SET0 PA.5                  ;set output of PA.5 to 0
      GOTO _STARTUP_IHRCR

P.S.: Just figured what you guys meant by using the SPI to generate a pulse. It was supposed to be slave-mode on the programmer, right?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 17, 2019, 06:20:35 am


Nice work, JS and Lucas. This looks much better than the original :) I would reorder the ADD A,1 as below, because otherwise the delay between the clock cycle and data may bee too low. This may lead to glitches with the SPI slave.


Code: [Select]
_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration

      ;user code here     


_CALIBRATION:
      T0SN PA.6                  ;read bit from PA.6
      ADD A,1                    ;increment A
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
      SET1 PA.5                  ;set output of PA.5 to 1
      SET0 PA.5                  ;set output of PA.5 to 0
      GOTO _STARTUP_IHRCR

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 17, 2019, 06:32:37 am
On the other hand, I likes JS proposal very much, which allows the programmer to control the actual calibration value: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2125579/#msg2125579 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2125579/#msg2125579)

With the sequential mode you have to go through 100+ steps of measuring and sending the signal to decrease. Since this is a very long sequence, there is a high probablity for a glitch to occur.  And there is no way to detect something is off, other than repeating the complete sequence again. Being able to control this value directly will allow to avoid this risk.

In addition, it is possible to use faster algorithms like a binary search. See for example the micronucleuos oscillator calibration. (C-Code is at the bottom). https://github.com/micronucleus/micronucleus/blob/master/firmware/osccalASM.S (https://github.com/micronucleus/micronucleus/blob/master/firmware/osccalASM.S)

Btw, I noticed now that it is not possible to remove the CLR A, from JS original code. However, I think it is possible to use "swapc IO.n" instruction to remove the sequence of "T1SN PA.6, OR A,1"? Example below. Sorry, I am in a hurry, maybe there is  stilla  bug.

Code: [Select]
_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
      GOTO _CALIBRATION          ;jump to calibration code, will be overwritten with NOP after calibration
     
      ;set SP, init .BSS, init .DATA, ...

      ;user code here

     
_CALIBRATION:
      MOV  A,0
      SET1 PAC.5                 ;PA.5 as output, rest as input  => this pin should exist on all devices, it is same as RESET pin
_CAL_TOGGLE_LOOP:
      SET1 PA.5                  ;set output of PA.5 to 1
      SET0 PA.5                  ;set output of PA.5 to 0

      SWAPC PA.6
      SLC A
      T0SN CF                    ;CF not set?
      GOTO _CAL_TOGGLE_LOOP
      GOTO _STARTUP_IHRCR

There surely are some peculiar instructions on the Padauk. But they all seem to be useful :)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 17, 2019, 12:22:43 pm
You can skip multiple IHRCR values at once simply by keeping pa6 high and counting pa5 pulses. Measuring takes a while, incrementing is fast.

You can double check for synchronization glitches at the end of calibration by fast skipping to IHRCR 0xff and 0x00, and redoing measurements. If the frequencies are far apart then we are ok.

If the frequencies end up close together then we missed a few steps and we were not at 0xff and 0x00. In this case simply reset and redo the calibration.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 17, 2019, 12:34:32 pm
According to the PMS150C datasheet it boots with ILRC not IHRC. May need setting CLKMD before calibration.
Sure.
CLKMD command should be precede any calibration and IHRC calibration is optional, same as a ILRC calibration (same scheme).

To avoid strict timing requirements the loop can be rewritten to make it slower. In the code below it should be safe to change PA.6 any time PA.5 is low, and it should stay low a lot longer than high. On the programmer set a rising edge-triggered interrupt on PA.5, busy-wait until cleared, then change PA.6.
Since on host (e.g. STM32) we can utilize a hardware SPI with DMA we can handle >24MHz SPI clock which for sure the IC will never achieve. But of course reordering is possible and should be done.

Also, accidentally shaved one instruction away. :-) At least if rewriting IHRCR and PAC with the same values has no side efects.
I like :-)


P.S.: Just figured what you guys meant by using the SPI to generate a pulse. It was supposed to be slave-mode on the programmer, right?
Yes.


Ok, now that calibration code is so short that we could think of 2 options:
* last 8 words of padauk IC specifies CRC (2words), ROLLING CODE (4 words) and holds the RET with the calibrated IHRC value.
 -> we could use this 7 words for calibration code (CRC seems to be stupid waste of space there and rolling code feature could be implemented different if required).

* I also found 1 more instruction to "shave": we could now place the short calibration code in startup directly and overwrite all 6 instructions with NOP after calibration

Code: [Select]
_STARTUP:
      MOV A,0xFF                 ;immediate value 0xFF with all bits 1, will be changed to MOV A,0x12 (0x12 = determined calibration value) after calibration was done
_STARTUP_IHRCR:     
      MOV IHRCR, A               ;set the calibration value
_CALIBRATION:
      SET1 PAC.5                 ;PA.5 as output (NOP after calibration)
      SET1 PA.5                  ;set output of PA.5 to 1  (NOP after calibration)
      T0SN PA.6                  ;read bit from PA.6  (NOP after calibration)
      ADD A,1                    ;increment A  (NOP after calibration)
      SET0 PA.5                  ;set output of PA.5 to 0 (NOP after calibration)
      GOTO _STARTUP_IHRCR

      ;user code here     


2+6 instructions :D

EDIT: Depending on CLKMD setting for WATCHDOG we might need to add a "WDRESET" instruction to the loop (optional +1)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 17, 2019, 01:57:01 pm
* I also found 1 more instruction to "shave": we could now place the short calibration code in startup directly and overwrite all 6 instructions with NOP after calibration

Depends. For the 8-core pdk16, there is only 8 bytes in between the fppa7 entry point and the irq handler. You rourinte is 2 + 6 bytes, but once the 6 are overwritten by nop, the next instruction is already in the interrupt handler, so there is no space left for the goto to the startup routine.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 17, 2019, 02:15:31 pm
* I also found 1 more instruction to "shave": we could now place the short calibration code in startup directly and overwrite all 6 instructions with NOP after calibration

Depends. For the 8-core pdk16, there is only 8 bytes in between the fppa7 entry point and the irq handler. You rourinte is 2 + 6 bytes, but once the 6 are overwritten by nop, the next instruction is already in the interrupt handler, so there is no space left for the goto to the startup routine.

Philipp

Startup does not need to be aligned at 0x000. Also there will be as set for CLKMD before and a WDRESET if required.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 17, 2019, 04:22:19 pm
Well I received yesterday some PFS154s, and I already have managed to get have them programmed. I've made the programmer as simple and as hobbyist-friendly as possible, using only DIP parts.

On the hardware size:

The boost converter is composed of L1, Q1, D1 and C1. The part values were mostly chosen at random until the circuit worked reliably. 1N4007 is possibly the worst choice but it's the only diode I have at the moment  ;D.

R1 is there to ensure the gate doesn't float, shorting the MOSFET. R2 and R3 form a 1/10 voltage divider for feedback. Q2 is required to cut voltage from the boost converter to the microcontroller during reset, and pass voltage only once it is stable.

VDD may be chosen from two different sources: from the SMPS through Q3, or from a fixed 3.3V supplied by a Holtek HT7133 linear regulator (U1) through Q4.

R5, R6, R7 and R8 form the standard voltage divider for data lines, for reducing 5V to 3.3V. I have settled on those values because higher ones (ie 3.3k/2.2k) introduced errors on the transmissions and I had to lower programming speed.

Now on the software side:

The Arduino's ADC is set to free running mode sampling from FB at the max allowed speed by the ATmega328 datasheet (1MHz). It is also set to use the internal 1.1V bandgap as reference, to avoid noise on the USB VCC to affect the quality of the regulation.

On every read sample, it is compared against a target voltage. If lower, the DRV pin is toggled. Otherwise, it is set to low. Given the 78KHz sampling rate, that means the buck frequency is around 37KHz at max current drain.

Now, to start a command (kudos to JS for the sequence):

For writing, after sending the command it sets VDD_33_EN to high impedance, and then immediately lowers VDD_SMPS_EN, thus connecting both VPP and VDD to 5.8V, which seems to be the required voltage for programming.

For wiping flash, after sending the command it then raises the target voltage to 6.5V, and then proceeds with the erase sequence.

I'm open to suggestions and improvements. I had thought about getting an ATtiny261, running V-USB on it and have the smallest and simplest, all-DIP programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 17, 2019, 04:37:47 pm
@socram: Great work.

I also got my programer PCBs today... This weekend I will solder everything and try to get it running. I tried to make it as cheap and flexible and small as possible (SMD 0603,  USB powered, multiple VPP and multiple VDD voltages for tuning)

JS

BTW: Somehow I managed with over voltage? to overwrite the PFS154 fixed chip ID section (with totally different value 0x0808). I still can read the IC reliable. The program inside does start but chip ERASE or WRITE to this section is not working anymore. Maybe I converted the flash part to OTP ?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Treehouseman on January 17, 2019, 04:48:23 pm
BTW: Somehow I managed with over voltage? to overwrite the PFS154 fixed chip ID section (with totally different value 0x0808). I still can read the IC reliable. The program inside does start but chip ERASE or WRITE to this section is not working anymore. Maybe I converted the flash part to OTP ?

Did you try repeating the process (over volting) to change the ID?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 17, 2019, 06:34:10 pm
BTW: Somehow I managed with over voltage? to overwrite the PFS154 fixed chip ID section (with totally different value 0x0808). I still can read the IC reliable. The program inside does start but chip ERASE or WRITE to this section is not working anymore. Maybe I converted the flash part to OTP ?

Did you try repeating the process (over volting) to change the ID?

Not yet. It was just an "accident". I had VPP at 12V and VDD at 8V for the PFS part (should be VPP 8.5V / VDD 5.9V), ... experiments...  :)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 17, 2019, 06:56:02 pm
@socram: I find the PNP transistors should be insufficient to block Vboost in reaching VPP and VDD. If Vboost>5V then the base voltage will be lower than the emitter's, there may be current, and the transistors may accidentally turn on.

I would suggest using 2 additional NPNs to connect VPP_EN and VDD_EN to ground when required.

An added bonus is that it would also work with 3.3V MCUs on the programmer.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 17, 2019, 07:07:12 pm
@socram: I find the PNP transistors should be insufficient to block Vboost in reaching VPP and VDD. If Vboost>5V then the base voltage will be lower than the emitter's, there may be current, and the transistors may accidentally turn on.

I would suggest using 2 additional NPNs to connect VPP_EN and VDD_EN to ground when required.

An added bonus is that it would also work with 3.3V MCUs on the programmer.
I found yesterday night that too, the hard way too, when I spent about one hour trying to figure out why the voltage didn't go to zero.

What I've done is drive them in an open collector mode. Instead of:
Code: [Select]
digitalWrite(pin, LOW);
...
digitalWrite(pin, HIGH);
I'm using:
Code: [Select]
digitalWrite(pin, LOW);
pinMode(pin, OUTPUT); // ground PNP base
...
pinMode(pin, INPUT); // high impedance PNP base
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 17, 2019, 08:27:57 pm
High Z may not help you, the high side mosfet of most GPIO has an intrinsic, non controllable, diode to VCC. As long as Vboost is higher than VCC (+2*Vdiode, but that is cutting close) you shouldn't be able to turn off the outputs.

Exceptions are the 5V tolerant IO on some 3.3V STM32, pins that are shared with VPP, and some dedicated/hardware open collector pins (like RA4 on PICs). Checking absolute maximum ratings should clarify that.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 17, 2019, 10:43:43 pm
Hmm that actually makes sense. I guess I'll try to replace it with a TO-92 p-channel MOSFET which shouldn't have this problem.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 17, 2019, 11:30:45 pm
P-mosfet will have the exact same issue. If Vgs < -2V it will turn on. 2V or something like that, look for Vgs_th for your mosfet.

If Vboost is above VCC+2V then you won't be able to turn it off.

Vg = high = VCC = 5V
Vs = Vboost = 10V (example)
Vgs = Vg-Vs = 5V-10V = -5V = on state

Vg=low makes it even more "on"

Try something like the circuit attached, where "+12V" is the boost output, "VPP" goes to the target, and VPPEN comes from the programmer MCU. I used AO3401 and AO3402 because I have hundreds, but any logic-level mosfet will do.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2019, 11:00:30 am
I'm open to suggestions and improvements. I had thought about getting an ATtiny261, running V-USB on it and have the smallest and simplest, all-DIP programmer.

FWIW, a few days ago I analyzed the analalog datalogs that Frank Buss took of the PFS154 programming sequence. Thanks to the high resolution analog recording it was possible to deduce the dataline direction (ICPDA) for some of the ambiguous cases.

Specifically, for your code:

The first three bits after command are driven from host. Not an issue the way you did it now.

Code: [Select]
uint16_t padauk_command(uint8_t cmd) {
  padauk_spi_write( 0xA5A, 12);
  padauk_spi_write(0x5A5A, 16);
  padauk_spi_write(cmd, 4);

/*
  padauk_spi_input();

  padauk_spi_clock();
  padauk_spi_clock();
  padauk_spi_clock();
*/
  padauk_spi_write(0, 3);

  padauk_spi_input();
  padauk_spi_clock();

  uint16_t ack = padauk_spi_read(12);

  padauk_spi_clock();
  padauk_spi_output();
  return ack;
}

This is important: The clock following the data is a bus reversal cycle. The slave will only free the bus after the rising edge, so you should only take back control after this clock cycle or risk shorts on the bus.

Code: [Select]
uint16_t padauk_flash_read(uint16_t addr) {
  padauk_spi_write(addr, 13);
  padauk_spi_input();
  uint16_t data = padauk_spi_read(14);
//  padauk_spi_output();
  padauk_spi_clock();
  padauk_spi_output();
  return data;
}

PDF here: https://github.com/cpldcpu/SimPad/tree/master/Protocol (https://github.com/cpldcpu/SimPad/tree/master/Protocol)*

*Just to clarify, I am not looking into creating a "competing" github repository to free-pdk. I'd be happy to put relevant information there. But I was honestly not aware who is running it due to a lack of identifiable members on the site. Also someone would need to grant write access to me.

Tim
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2019, 11:06:17 am
Quote
    Well I received yesterday some PFS154s, and I already have managed to get have them programmed. I've made the programmer as simple and as hobbyist-friendly as possible, using only DIP parts.

    For writing, after sending the command it sets VDD_33_EN to high impedance, and then immediately lowers VDD_SMPS_EN, thus connecting both VPP and VDD to 5.8V, which seems to be the required voltage for programming.

Very nice! I like the idea of using VPP=VDD for for PFS154 to reduce circuit complexity.

Regarding controlling VDD or VPP when it is higher than the MCU voltage. Maybe one way of doing this could be how it is done in the PicKit. This is actually also what Lucas proposed above. See here: https://pic-microcontroller.com/wp-content/uploads/2013/04/Schematic-PICkit-2.jpg

Q3 forms an inverter to generate a higher control voltage and Q4 switches Vpp.

Quote
    I'm open to suggestions and improvements. I had thought about getting an ATtiny261, running V-USB on it and have the smallest and simplest, all-DIP programmer.

One challenge is that V-USB will occupy all interrupt time. So this would conflict with the way you are controlling the boost converter now. One option could be to let the booster "coast" during USB transmissions. One other challenge will be, that you somehow have to deal with the fact that no USB transmission can be accepted during programming. This would require special timing from the host program. In principle it could be possible to do it in a similar way to micronucleus. Everything would be much easier though when not having to deal with soft-USB :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 18, 2019, 11:17:31 am
Thanks for the tips about the timing of the writes.

Regarding the voltage generation, I am considering replacing the whole thing with two buck/boost 2-switch converters, so I can switch the VCC before going inside the converter, rather than the 8V coming from the converter. That would also let me remove the HT7133.

I was also considering changing the ADC ISR, from instead of controlling directly the drive pin, to adjusting PWMs duty cycle, so it can be left running somewhat unattended while servicing V-USB interrupts.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2019, 11:55:49 am
Regarding the voltage generation, I am considering replacing the whole thing with two buck/boost 2-switch converters, so I can switch the VCC before going inside the converter, rather than the 8V coming from the converter. That would also let me remove the HT7133.

I think you still need a way to switch on and off VDD. If you rely only on the boost converter there will be very slow ramps. This could lead to malfunctioning of the reset circuit in the MCU. This could be a rare occurence, though.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 18, 2019, 12:08:23 pm
So here's a comparison table of the different versions of the circuit I'm considering, with new schematics attached:
VersionLDOsNMOSPNPsNPNsDiodesInductorsResistorsCapacitorsVDD rangeVPP range
v1 (original)113011823.3V + 5V~8V5V~8V
v1 (fixed high-side)1330111023.3V + 5V~8V5V~8V
v2002222820V~8V5V~8V
The fixed v1 is just too complex due to the fixed high-side switches and doesn't really have any advantages at this point over having two completely independent DC-DC converters from the v2, so I'm kinda biased towards v2.

I've replaced NMOS with digital transistors, mostly because they are cheaper, we're dealing with very low current, and I can also avoid the external resistors connecting the gate to ground of the MOSFET, simplifying even further the board.

I think you still need a way to switch on and off VDD. If you rely only on the boost converter there will be very slow ramps. This could lead to malfunctioning of the reset circuit in the MCU. This could be a rare occurence, though.
I'm not sure that would affect any modern microcontrollers, specially if they have low-voltage resets and brown-out resets such as these. I guess there's just one way to be sure about it - trying  ;D

EDIT: Here's the EasyEDA schematic, in case anybody wants to improve or toy with it: https://easyeda.com/socram8888/padauk-programmer

EDIT2: Alternatively, we could use a SEPIC DC-DC converter, which shaves down two diodes and the PNP, in exchange for two inductors.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 18, 2019, 01:21:17 pm
*Just to clarify, I am not looking into creating a "competing" github repository to free-pdk. I'd be happy to put relevant information there. But I was honestly not aware who is running it due to a lack of identifiable members on the site. Also someone would need to grant write access to me.
Tim

Added you to free-pdk organization on github*.

*You just never asked to be added.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 19, 2019, 08:12:25 am
Added you to free-pdk organization on github*.

Thanks a lot! I will put the programming protocol information there.

Btw, in general:

It seems like every other padauk device is using a different programming algorithm. So far, only two are known: PFS154 ("5-wire", confirmed twice), PMS150C ("six-wire". The PMC150C algorithm also works on the PMS154C, when changing datalen.

I tried a couple of other device:
   - PMC251 uses six-wire physical interface, but was unresponsitve with the PMC150C algorithm
   - PMS131 uses an eight-wire physical interface and seven when in an 8-pin package

It could get quite tedious to also decode all devices. Hopefully all MTP devices will use the 5-wire protocol.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 19, 2019, 08:32:21 am
The assembler was contributed by Nicolas Lesser. I just merged a patch by him that fixes this issue.
Philipp

What would be the best way to get feedback and patches to him? I found and fixed a bug in enconding SL/SLC/SR/SRC. Fix attached.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 19, 2019, 03:10:39 pm
The assembler was contributed by Nicolas Lesser. I just merged a patch by him that fixes this issue.
Philipp

What would be the best way to get feedback and patches to him? I found and fixed a bug in enconding SL/SLC/SR/SRC. Fix attached.

To get the patches to him, I'd suggest opening an issue or pull request at his repo:

https://github.com/Rakete1111/sdcc-pdk

Alternatively, you can open a ticket in the SDCC patch tracker, from where an SDCC developer (e.g. me) would apply it to the assembler in the SDCC pdk branch:

https://sourceforge.net/p/sdcc/patches/

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 19, 2019, 03:16:27 pm
Added you to free-pdk organization on github*.

Thanks a lot! I will put the programming protocol information there.

Btw, in general:

It seems like every other padauk device is using a different programming algorithm. So far, only two are known: PFS154 ("5-wire", confirmed twice), PMS150C ("six-wire". The PMC150C algorithm also works on the PMS154C, when changing datalen.

I tried a couple of other device:
   - PMC251 uses six-wire physical interface, but was unresponsitve with the PMC150C algorithm
   - PMS131 uses an eight-wire physical interface and seven when in an 8-pin package

It could get quite tedious to also decode all devices. Hopefully all MTP devices will use the 5-wire protocol.

How about the PFS173? From the datasheet it looks as if it uses the same pins as the PFS154.
On the other hand, my information on the PFC232 and PFS232 indicates that these two use an interface different from the PFS154, and PA4 has a role in programming them (for a total of 6 pins in the interface).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 19, 2019, 04:00:49 pm

To get the patches to him, I'd suggest opening an issue or pull request at his repo:

https://github.com/Rakete1111/sdcc-pdk

Thanks, done!

How about the PFS173? From the datasheet it looks as if it uses the same pins as the PFS154.
On the other hand, my information on the PFC232 and PFS232 indicates that these two use an interface different from the PFS154, and PA4 has a role in programming them (for a total of 6 pins in the interface).

Just guessing: PFS173 and PFS154 are probably identical, since the adresslength is sufficient. No ideay about the PFC/PFS232, I have not seen any datasheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 19, 2019, 11:39:40 pm
I assembled the 2 PCBs of my "easy pdk programmer" today.

- complete design process was done using EasyEDA + JLPCB  + LCSC.
- learning how to use EasyEDA was very easy
- ordering on JLPCB was smooth and very good price ($2 for 10 PCBs, if you panelize then you might get 40 programmer PCBs for just $2 + shipping)
- ordering components at LCSC based on EasyEDA BOM was also very easy, they offer to combine shipment with JLPCB so you pay shipping ($5 for normal delivery) only once.
- it only took 8 days from ordering PCB + components till arrival *wow*

- both assembled boards are working (tested basic functions: generate +15V, dual DAC+opamp can output specific voltages, USB ok, LEDs ok, button ok, ...)
- only 1 small mistake on test PCB (forgot to connect something to ground, was easy to fix with a jumper wire)

I will test programing a PFS154 and some other ICs within the next days. Hopefully getting everything ready before chinese new year starts (China closes on 30th of January for 2-3 weeks).

JS

P.S. I will upload schematics, gerber and firmware sources to github as soon as the stable programmer is confirmed working.

PPS:

The PCB on top of the picture is having the optional 4 pin SWD header for easy debugging. The PCB on bottom is having an optional GND pin for easy oscilloscope measurements. Both of this optional components are not required for normal operation of the programmer later.
The missing components are caused by choosing a different DCDC booster and by getting rid of the not required level shifter.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 20, 2019, 01:01:15 pm
- both assembled boards are working (tested basic functions: generate +15V, dual DAC+opamp can output specific voltages, USB ok, LEDs ok, button ok, ...)
- only 1 small mistake on test PCB (forgot to connect something to ground, was easy to fix with a jumper wire)
Nice!

May I suggest one addition for the next revision of the board:

Add another row of 8 holes in 2.54mm raster, spaced 15.24mm (6 rows in 2.54mm raster) from the current one. Connect all the holes to GND.

This would allow to later create small adapter pcbs, which can then be securely plugged on top of the programmer with pin header sockets. In these adapter pcbs you can then plug in programming sockets for the Padauk controllers.

See here for details of the idea: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2105053/#msg2105053 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2105053/#msg2105053)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 20, 2019, 02:10:31 pm
Nice!

May I suggest one addition for the next revision of the board:

Add another row of 8 holes in 2.54mm raster, spaced 15.24mm (6 rows in 2.54mm raster) from the current one. Connect all the holes to GND.

This would allow to later create small adapter pcbs, which can then be securely plugged on top of the programmer with pin header sockets. In these adapter pcbs you can then plug in programming sockets for the Padauk controllers.

See here for details of the idea: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2105053/#msg2105053 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2105053/#msg2105053)

My initial idea was to go sideways.
I already created a small adapter PCB with a ZIF20 DIP small socket which can get connected to the 8 pins directly but also has pin header for every pin of the ZIF20 socket so it can be used as a generic adapter with jumper wires. This allows all PADAUK ICs to be written regardless of the pinout.
There are many cheap adapters from TSOP to DIP which  can be used easily in the ZIF20 socket.

Anyway I also like the on top idea. But new problems will arise like can not see LEDs or reach user button anymore, ...

I will do some experiments and report back here. Several ZIF TSOP and adapter PCBs are on the way to me now.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 20, 2019, 02:35:22 pm
My initial idea was to go sideways.
Yes, that would also work. But in my experience sideways going female headers (the ones that would go on the next pcb to the side) are more expensive and more rare than the straight ones. That is why I'd prefer to go on top.
 
I already created a small adapter PCB with a ZIF20 DIP small socket which can get connected to the 8 pins directly but also has pin header for every pin of the ZIF20 socket so it can be used as a generic adapter with jumper wires. This allows all PADAUK ICs to be written regardless of the pinout.
Jumper wires are ok during programmer development. But I'd like to avoid them for regular use afterwards: they tend to create EMI problems and sometimes make bad contacts. So I'd prefer a solution with adapter pcbs which are made for one kind of Padauk controller. You can fit a lot of different ones on one 10x10 pcb.

Anyway I also like the on top idea. But new problems will arise like can not see LEDs or reach user button anymore, ...
You could move the button to where the URL text is now.

BTW, what do you plan to use the button for?

I'd also suggest to add another button connected BOOT0 to boot with the integrated usb bootloader. That way you don't need a SWD programmer for initial programming. This would make it easier for people to make their own padauk programmers when they don't regularly use STM32 or other controllers with SWD interface.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 20, 2019, 03:29:31 pm
Quote
Posts: 101
Country: ht
View Profile  Personal Message (Offline)

Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
« Reply #479 on: Yesterday at 10:39:40 am »
Say ThanksReplyQuote
I assembled the 2 PCBs of my "easy pdk programmer" today.

- complete design process was done using EasyEDA + JLPCB  + LCSC.
- learning how to use EasyEDA was very easy
- ordering on JLPCB was smooth and very good price ($2 for 10 PCBs, if you panelize then you might get 40 programmer PCBs for just $2 + shipping)
- ordering components at LCSC based on EasyEDA BOM was also very easy, they offer to combine shipment with JLPCB so you pay shipping ($5 for normal delivery) only once.
- it only took 8 days from ordering PCB + components till arrival *wow*

- both assembled boards are working (tested basic functions: generate +15V, dual DAC+opamp can output specific voltages, USB ok, LEDs ok, button ok, ...)
- only 1 small mistake on test PCB (forgot to connect something to ground, was easy to fix with a jumper wire)

I will test programing a PFS154 and some other ICs within the next days. Hopefully getting everything ready before chinese new year starts (China closes on 30th of January for 2-3 weeks).

JS

P.S. I will upload schematics, gerber and firmware sources to github as soon as the stable programmer is confirmed working.

PPS:

The PCB on top of the picture is having the optional 4 pin SWD header for easy debugging. The PCB on bottom is having an optional GND pin for easy oscilloscope measurements. Both of this optional components are not required for normal operation of the programmer later.
The missing components are caused by choosing a different DCDC booster and by getting rid of the not required level shifter.

Great work :-+ :-+ :-+
I can do the schematic and PCB in Altium too! after you release the stable version. ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on January 20, 2019, 04:36:26 pm
I'd also suggest to add another button connected BOOT0 to boot with the integrated usb bootloader. That way you don't need a SWD programmer for initial programming. This would make it easier for people to make their own padauk programmers when they don't regularly use STM32 or other controllers with SWD interface.

Having the serial bootloader accessible would be nice, but it missing is not a deal breaker.

You can use any Linux SBC's GPIO with openocd to do debugging over JTAG/SWD. It is very likely that anyone adventurous enough to look at Padauk MCUs will have a raspberry pi lying around.

A script (or self contained appimage) that does the flashing with a single command would be nice, though.

Enviado de meu SM-N910C usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 20, 2019, 04:51:09 pm
My initial idea was to go sideways.
Yes, that would also work. But in my experience sideways going female headers (the ones that would go on the next pcb to the side) are more expensive and more rare than the straight ones. That is why I'd prefer to go on top.
I found femal sideways header on LCSC (you are right, it was tricky).

I already created a small adapter PCB with a ZIF20 DIP small socket which can get connected to the 8 pins directly but also has pin header for every pin of the ZIF20 socket so it can be used as a generic adapter with jumper wires. This allows all PADAUK ICs to be written regardless of the pinout.
Jumper wires are ok during programmer development. But I'd like to avoid them for regular use afterwards: they tend to create EMI problems and sometimes make bad contacts. So I'd prefer a solution with adapter pcbs which are made for one kind of Padauk controller. You can fit a lot of different ones on one 10x10 pcb.
A lot of changes are requested/required (e.g. mounting holes, adapter on top, ...) I will see how much I can put into it.

Anyway I also like the on top idea. But new problems will arise like can not see LEDs or reach user button anymore, ...
You could move the button to where the URL text is now.
BTW, what do you plan to use the button for?
Was just a thought. Like the original PADAUK programmer. Maybe later you can transfer the image to programmer and then press the button to program (no need of computer).

I'd also suggest to add another button connected BOOT0 to boot with the integrated usb bootloader. That way you don't need a SWD programmer for initial programming. This would make it easier for people to make their own padauk programmers when they don't regularly use STM32 or other controllers with SWD interface.
Will do that, I try to connect the user button also to BOOT0.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 20, 2019, 04:59:12 pm
Having the serial bootloader accessible would be nice, but it missing is not a deal breaker.
Since ST-LinkV2 (china clone) costs less than $2 there is really no point anymore to use the serial boot loader.
For the price of just a USB serial adapter you get a full featured SWD debugger which opens the REAL world of software development (fast uploading, breakpoints, watched variables, ...).

I only can strongly recommend to switch to real software development (use JTAG/SWD and a debugger) and avoid the "printf debugging" introduced by Arduino.
Setting up and learning how to use the free open source tool chains for real development and debugging is dead simply nowadays. And it is possible to use all Arduino libraries and sample code.
Just ditch the Arduino IDE!

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 20, 2019, 05:37:30 pm
A lot of changes are requested/required (e.g. mounting holes, adapter on top, ...) I will see how much I can put into it.
I offer to make some adapter pcbs for different padauk ics and publish the sources & gerbers for others to use. So no extra work for you creating adapter pcbs. But I'll wait for you to publish a programmer layout with holder pins first.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 21, 2019, 08:41:46 pm
I assembled the 2 PCBs of my "easy pdk programmer" today.
...
I will test programing a PFS154 and some other ICs within the next days. Hopefully getting everything ready before chinese new year starts (China closes on 30th of January for 2-3 weeks).
Great work, very clean build!

Any success with programming so far? :)

I only can strongly recommend to switch to real software development (use JTAG/SWD and a debugger) and avoid the "printf debugging" introduced by Arduino.
Setting up and learning how to use the free open source tool chains for real development and debugging is dead simply nowadays. And it is possible to use all Arduino libraries and sample code.
Just ditch the Arduino IDE!

Well, it looks like we are stuck with "printf debugging" with the Padauk controllers though. One thing I implemented was to use the programming interface as an SPI backchannel. The "programmer" (I am referring to my breadboard contraption) is resetting the MCU and is then listening to SPI transmissions on the programming interface lines as a slave. This allowed some degree of debugging. This may be an interesting addition to the firmware of your programmer as well.



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 21, 2019, 08:48:16 pm
FYI, I worked on more assembler code based on the OSS toolchain, mainly using SDASPDK. You can find some examples for the PFS154 here:

https://github.com/cpldcpu/SimPad/tree/master/PFS154Examples (https://github.com/cpldcpu/SimPad/tree/master/PFS154Examples)

They are tested on actual hardware.

"blinkyasm.c" should assemble with the current version of SDASPDK from Phillips branch. The other examples need the patch that I posted above. It is on it's way upstream, though.

Edit: Just noticed, the patch is already there. Looks like I need a cron job to update SDCC :)




Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 22, 2019, 11:55:33 am
Any success with programming so far? :)
Not much time right now. I just got ADC working properly (was mistake with a resistor in schematic). Next part is trying to reduce ripple (everything is a bit noisy right now so I will play a bit with different cap values / adding some caps).

For programing I'm swapping pins around so the hardware SPI and a complete TIM is available on right pins.

Well, it looks like we are stuck with "printf debugging" with the Padauk controllers though. One thing I implemented was to use the programming interface as an SPI backchannel. The "programmer" (I am referring to my breadboard contraption) is resetting the MCU and is then listening to SPI transmissions on the programming interface lines as a slave. This allowed some degree of debugging. This may be an interesting addition to the firmware of your programmer as well.

Excellent idea / addition. This can be added to the programmer USB protocol as a debug channel.

But do you think SPI is a good choice? I used it in a previous test and had the problem that if a single bit was missing (e.g. after startup) the complete output was garbled.
spth made a small demo with a very simple UART. Maybe we should choose this method as it can handle transmission errors more easy (e.g. require 2 stop bits and we can resync).
Or we use SPI with CS(NSS) but then 1 more wire required.

JS

UPDATE:
This is the hardware mapping I have available after swapping pins:

STM_PB3: SPI1_SCK  / TIM2_CH2      (IC_PA3)
STM_PB4: SPI1_MISO / TIM3_CH1     (IC_PA4)
STM_PB5: SPI1_MOSI / TIM3_CH2     (IC_PA6)   (SPI slave mode on STM uses MOSI to get data from IC)
STM_PB6: UART1_TX  / TIM16_CH1N (IC_PA0)
STM_PB7: UART1_RX  / TIM17_CH1N (IC_PA7)


* IC_PA3 requires to have the SPI1_SCK, also the dedicated TIM is required to capture input pulses during calibration (note: TIM2 additional channels can not be shared with PWM or other functions)
* IC_PA4 requires SPI1_MISO (input of IC <= output of STM32)
* IC_PA6 requires SPI1_MOSI (output of IC => input to STM32)
* UART1_TX / UART1_RX can be used for debugging and also for serial boot loader of STM32, no special requirement for IC pins
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 22, 2019, 01:02:56 pm
But do you think SPI is a good choice? I used it in a previous test and had the problem that if a single bit was missing (e.g. after startup) the complete output was garbled.
spth made a small demo with a very simple UART. Maybe we should choose this method as it can handle transmission errors more easy (e.g. require 2 stop bits and we can resync).
Or we use SPI with CS(NSS) but then 1 more wire required.
I have bad experience with several kinds of CS-less SPI variants. You need a mechanism like CS, otherwise your transfer quickly becomes unreliable.

I'd much prefer a software UART for debugging. You just need one TX line and that's it, no additional clock or CS. Also you wouldn't necessarily need the programmer to read the output, any UART dongle will do. So you also wouldn't need any code for it in the programmer firmware (but it wouldn't hurt of course if someone wants to write it).

The only problem could be to detect the correct baud rate as the internal clock of the Padauk could be off. So I suggest to send a 0x55 ("U") character first. It has a 10101... pattern and is commonly used for autobaud mechanisms.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 22, 2019, 08:45:41 pm
Yes, I agree, an UART would be much nicer. I was not sure how much the clock in my devices was miscalibrated, so it was much quicker to implement SPI. I worked around the misalignment issue by introducing a timeout.

Having an UART with autobaud would be the best option, but it's a bit more involved to implement this on host side. How would you do bitrate detection? By bitbanging? Or oversampling with DMA?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 22, 2019, 09:29:01 pm
Having an UART with autobaud would be the best option, but it's a bit more involved to implement this on host side. How would you do bitrate detection? By bitbanging? Or oversampling with DMA?
The STM32 have autobaud hardware, see AN4908: https://www.st.com/content/ccc/resource/technical/document/application_note/group0/66/fa/62/a2/5c/75/48/a8/DM00327191/files/DM00327191.pdf/jcr:content/translations/en.DM00327191.pdf (https://www.st.com/content/ccc/resource/technical/document/application_note/group0/66/fa/62/a2/5c/75/48/a8/DM00327191/files/DM00327191.pdf/jcr:content/translations/en.DM00327191.pdf)

On the STM32F072 only UART1 and 2 have autobaud, so the TX pin of the Padauk should be connected to any of these pins on the STM32: PA3(*), PA10, PA15, PB7
(*) TTa Analog IO, pin is only allowed to go up to 3.3V, so we'd need an extra buffer ic in between to protect the pin from 5V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 23, 2019, 09:01:16 pm
I adapted SDAS to PDK13, so it is now also possible to use a OSS toolchain for the true "$0.03 MCU". Not sure whether this will be available upstream anytime soon, as there is still some work to be done to allow PDK13 and PDK14 to coexist in SDCC. (Frankly, that is probably the harder part...)

In any case, I uploaded some (verified) code examples here:
https://github.com/cpldcpu/SimPad/tree/master/PMS150CExamples

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: _echo on January 26, 2019, 12:11:52 am
On the topic of VPP generation there is a family of parts that might be useful if you happen to have them handy and have a breakout board.
There are specialty(ish) DACs called programmable gamma buffers such as the ISL76534.

They can be referenced to a quite high voltage (up to 19V), configured over i2c, and have fairly good current capability (for a DAC).

My plan is to build up a programmer using the PGB + cheap boost module from aliexpress as the VPP/VDD generator. By setting setting the boost converter to output 16.384V, the math is also simpler making runtime vpp/vdd calculation possible.

Nothing against the host MCU generated PWM scheme, it's certainly economical. IMHO, those boost modules are cheap enough to use as the source of high voltage, and eliminates the risk of getting the boost converter stuck when doing ISP of the AVR.

Still waiting for my chips to come in before I confirm that these parts can be programmed with this guy providing power.

Regards
_echo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on January 26, 2019, 02:30:25 am
Getting the PWM stuck isn't really that much of a problem. The ISP runs on reset, and on reset all pins are set as inputs and PWMs are stopped.

Regarding my programmer, I have finally settled on the following:

It will be made with all DIP parts, to make prototyping and soldering for newbies easier. Still, given how few components this have it won't be too big.

The MCU is gonna be an ATtiny84A running at 20MHz, which I received yesterday. This part is tiny (14 pins), cheap (~1€ each), yet has all the features I need for this: two PWM, two DAC inputs and enough flash/RAM for V-USB. It's also available in both DIP and SMD packages, both from LCSC and from western providers such as Mouser or RS.

I'll be using V-USB with HID for controlling the programming sequence. This means no driver needed on either Windows or Linux. It also means the firmware will be self-updating using any computer with no specialized programmer thanks to the Micronucleus bootloader I've previously tried and used.

After considering the original buck+linear, the buck+boost design, and the SEPIC design, I'm gonna go with a pair of completely independent SEPIC DC-DC converter for voltage generation. SEPIC means I will be needing a single PWM channel, thus simplifying a lot the algorithm for keeping the voltage supply stable, and a single MOSFET for controlling an output from all the way to zero when stopped, up to about 9V.

I'm waiting to receive the MOSFETs and Schottky diodes from LCSC. Will keep you updated guys.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 26, 2019, 07:41:43 pm
I adapted SDAS to PDK13, so it is now also possible to use a OSS toolchain for the true "$0.03 MCU". Not sure whether this will be available upstream anytime soon, as there is still some work to be done to allow PDK13 and PDK14 to coexist in SDCC. (Frankly, that is probably the harder part...)

Where can I find this sdas for pdk13? How is the target selected? An assembler directive similar to how ".cs08" switches the hc08 assembler to s08 mode and .hd64 switches the z80 assembler to z180 mode?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 26, 2019, 08:57:35 pm

Where can I find this sdas for pdk13? How is the target selected? An assembler directive similar to how ".cs08" switches the hc08 assembler to s08 mode and .hd64 switches the z80 assembler to z180 mode?

Philipp


I linked it in an issue in Nicolas fork of SDCC.

https://github.com/Rakete1111/sdcc-pdk/issues

He seems to be busy though. I simply modified the existing source to support PDK13 instead of PDK14. I made no attempts to create a switch or similar. That is probably something that someone who is more familiar with the structure of SDAS should do. I also found additional bugs in PDK14.

Title: STT/LDT instruction encoding
Post by: tim_ on January 27, 2019, 08:43:13 am
Code: [Select]
0 0 0 0 1 1 c 7-bit MEM addr c 16 bit memory operations
0x03.. 0 0 0 0 1 1 0 M 0 STT16 M M ← Timer16 (last bit of M set to 0, M must be word aligned)
0x03.. 0 0 0 0 1 1 0 M 1 LDT16 M Timer16 ← M (last bit of M set to 1, M must be word aligned)

One question about the STT/LDT instruction encoding: The bitfield for the memory address is only 7 bits instead of 8. Which bit of the address is discarded? The MSB or LSB? Since the adress is word-aligned, it should be fine to discard the LSB.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on January 27, 2019, 09:12:54 am
lsb will always be 0, the bits in the opcode are in the correct bit position, just make bit 0 be 0 always.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 29, 2019, 07:29:00 am
lsb will always be 0, the bits in the opcode are in the correct bit position, just make bit 0 be 0 always.


Thanks! That makes a lot of sense, indeed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 29, 2019, 01:07:54 pm
Project update for "Easy PDK Programer":

First of all... IT'S ALIVE. Programing PFS154 and PFS154B worked flawlessly.

After some modifications to the test pcb (thanks to your comments and some testing) following things got improved:

- use MT3608 as dc-dc-booster
- user button can be used to enter STM32 ROM bootloader for USB-DFU (easy to change firmware, can not get "bricked")
- generated VDD/VPP voltage is very stable (ripple <20mV)
- moved pins around to completely free up TIM2 for IC calibration
- moved pins around to be able to use hardware SPI for IC calibration
- moved pins around to be able to have a serial port on 5V tolerant pins going to IC for easy debugging
- added two 8 pin female header to plugin adapter for programing on top (not going to side anymore)
  => the 8 pin rows are connected that a standard TSOP16-DIP adapter can be plugged in directly and many PADAUK IC variants (esp. the flash variants like PFS154) can be programmed without an additional adapter PCB.
  => adapter PCB can be designed easily for other types and plugged on top
  => the unused connector pins are not connected to anything on purpose so they will not connect unused IC pins during programing (when using the TSOP adapter directly).

Some pictures:

The first 3 pictures show the modded 1.1 pcb (used to verify) improvements with different attachments of adapter / sockets / ... . The last 2 show the (hopefully final) schematic and pcb (just ordered).

BTW: Thanks for the tip with panelize. I will get 40 pcbs this time for $2 + shipping :)
So total cost again reduced: BOM+PCB now smaller than $2 :-)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on January 29, 2019, 06:01:52 pm
Big thumbs up js_12345678_55AA  :-+ :-+ :-+

Is there progress regarding the rest of the family?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on January 29, 2019, 08:40:14 pm
Big thumbs up from me too  :-+

- added two 8 pin female header to plugin adapter for programing on top (not going to side anymore)
  => the 8 pin rows are connected that a standard TSOP16-DIP adapter can be plugged in directly and many PADAUK IC variants (esp. the flash variants like PFS154) can be programmed without an additional adapter PCB.
  => adapter PCB can be designed easily for other types and plugged on top
good idea.

So your plan is that you usually solder a DIP 16 ZIF socket directly onto the programmer pcb and then plug a SOIC adapter into the zif socket. Optionally you can plug in adapter pcbs into the zif socket. Correct?
Or do you not want to use the zif socket and use female pin headers instead and plug the SOIC adapter into them?

A zif socket like this: https://www.aliexpress.com/item//32905413905.html (https://www.aliexpress.com/item//32905413905.html) has a width of 15mm. Did you check if there is enough space on your pcb? The footprint on the bottom right, a bit left to the zif socket, looks very close to me. It is probably for the button.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 30, 2019, 11:07:46 am
So your plan is that you usually solder a DIP 16 ZIF socket directly onto the programmer pcb and then plug a SOIC adapter into the zif socket. Optionally you can plug in adapter pcbs into the zif socket. Correct?
Or do you not want to use the zif socket and use female pin headers instead and plug the SOIC adapter into them?

Neither of this.

Like I wrote I will add two 8 pin female header (like arduino female header).

In this header you can plug the TSOP/SOIC adapter (you can see in the pictures) directly.

If you want to use a ZIF socket or any other socket it is easy to build an adapter pcb (like an arduino shield).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 06, 2019, 11:58:30 am
Hi,

since PCB delivery is delayed due to Chinese new year a friend and I played a bit making a 3D printable case for the Easy PDK Programmer.

In the pictures below you can see a first case version and mocks of the final look. The round hole will hold a 3D printed button and the long hole will get a transparent inlay for the led to shine through.

I also made some progress with the programmer firmware. Serial input for debugging from IC with auto baud detection and forwarding over USB is working. Next thing on my list is calibration.

Have fun,

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: mikeselectricstuff on February 06, 2019, 01:25:41 pm
Hi,

since PCB delivery is delayed due to Chinese new year a friend and I played a bit making a 3D printable case for the Easy PDK Programmer.
why... :palm:
Just design the PCB to fit a standard Hammond box.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 06, 2019, 02:37:20 pm
Hi,

since PCB delivery is delayed due to Chinese new year a friend and I played a bit making a 3D printable case for the Easy PDK Programmer.
why... :palm:
Just design the PCB to fit a standard Hammond box.

Why? Because we can ;D

You also can mount the pcb in a "Hammond box", do some cutting for USB and the pin header and end up with a boring square case where the case alone costs more than the complete programmer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: mikeselectricstuff on February 06, 2019, 06:44:00 pm
Hi,

since PCB delivery is delayed due to Chinese new year a friend and I played a bit making a 3D printable case for the Easy PDK Programmer.
why... :palm:
Just design the PCB to fit a standard Hammond box.

Why? Because we can ;D

You also can mount the pcb in a "Hammond box", do some cutting for USB and the pin header and end up with a boring square case where the case alone costs more than the complete programmer.
..and how much time & material does a crappy-looking 3D printed case cost ?

If you use something like these, you can use PCBs as end panels, so no manual  hole cutting etc. 
https://www.hammfg.com/electronics/small-case/plastic/1593 (https://www.hammfg.com/electronics/small-case/plastic/1593)
(https://www.hammfg.com/files/images/electronics/electronics/1593-gray-pcb-200w.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 06, 2019, 09:47:40 pm
Hi,

since PCB delivery is delayed due to Chinese new year a friend and I played a bit making a 3D printable case for the Easy PDK Programmer.
why... :palm:
Just design the PCB to fit a standard Hammond box.

Why? Because we can ;D

You also can mount the pcb in a "Hammond box", do some cutting for USB and the pin header and end up with a boring square case where the case alone costs more than the complete programmer.
..and how much time & material does a crappy-looking 3D printed case cost ?

If you use something like these, you can use PCBs as end panels, so no manual  hole cutting etc. 
https://www.hammfg.com/electronics/small-case/plastic/1593 (https://www.hammfg.com/electronics/small-case/plastic/1593)
(https://www.hammfg.com/files/images/electronics/electronics/1593-gray-pcb-200w.jpg)

Crappy? I think this is a personal opinion.

I printed it with a very fine resolution (0.2mm nozzle, 0.1mm layer height) so it  took a bit longer than needed, however your can print this in less than 30 minutes.

Here the stats:
Build time: 1 hours 43 minutes
Filament length: 2200.6 mm
Plastic weight: 6.62 g (0.01 lb)
Material cost: 0.30 USD

(3D printer used from our local hacker space, Filament used PET-G, not this rubbish ABS).

So not sure how fast you get those expensive cases you mentioned delivered or do you work for them?
The box you mentioned (e.g. 1593KBK) costs around 3.68 USD.

The programmer PCB + components is less than 2 USD + 0.30 USD for the 3D printed cases. All together still less than the much bigger, space wasting  1593KBK box.

Also if somebody does not like it, he can change it, make a new one or even use some commercial stuff.


And best part (before you can rant about this). The custom printed case DOES SHOW THE PINOUT (printed on PCB)  ;D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 07, 2019, 04:03:50 pm
Regarding calibration I came up with the following idea:

(I will use SDCC from now on for any future development)

If somebody wants to insert calibration in a program we can do this by using a sequence of NOP instructions.
So if somebody compiles the program and uses a programmer which does not support calibration the NOP sequence will not do any harm.

Now the trick. Instead of using plain simple NOPs I plan to use a sequence of "AND A, ..."
Since it is absolutely impossible that someone wants to AND A a times in a row with different values we can use the immediate 8 bit value to encode information and have a strong marker:

and a, #'I'
and a, #'H'
and a, #'R'
and a, #'C'
and a, #(16000000)
and a, #(16000000)>>8
and a, #(16000000)>>16
and a, #(16000000)>>24

Like this we can encode a marker ("IHRC" for calibration of internal high speed RC / "ILRC" of the internal low speed RC) and the desired tuning frequency.
If you compile and flash the code with another programmer without doing calibration it will just do 8 ANDs and most likely result in A=0 since frequency>>24 is for sure not desired ;-)

Easy-PDK-Writer now can scan the binary for the magic ANDs with 'I' 'H' 'R' 'C' / 'I' 'L' 'R' 'C' + frequency value, dynamically insert the calibration code, write the IC, do the calibration, write the calibration result to IC and change the calibration code to NOPs.

TO make it more convenient I wrote 2 macros for SDCC:

Code: [Select]
#define EASY_PDK_CALIBRATE_IHRC(frequency) \
__asm__(                      \
  "and a, #'I'                \n"\
  "and a, #'H'                \n"\
  "and a, #'R'                \n"\
  "and a, #'C'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
)
Code: [Select]
#define EASY_PDK_CALIBRATE_ILRC(frequency) \
__asm__(                      \
  "and a, #'I'                \n"\
  "and a, #'L'                \n"\
  "and a, #'R'                \n"\
  "and a, #'C'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
)

So if you want to insert calibration to your program you only have to add one line to _sdcc_external_startup after setting clkmd:

Code: [Select]
unsigned char _sdcc_external_startup(void)
{
  clkmd = 0x34;                       // Use IHRC / 2 = 8 Mhz for system clock, disable ILRC, disable watchdog
  EASY_PDK_CALIBRATE_IHRC(8000000);   // calibrate IHRC to 8 MHz system clock
  return 0;
}


What do you think?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on February 07, 2019, 05:57:15 pm
I like the idea of using the #defines for inserting the calibration routine into the code. That is convenient.

But how about this change: The asm code in the define is the actual calibration routine used. That makes what actually happens more obvious to the user and is less of a magic number.

The programmer then writes the unmodified program to the controller and does the calibration.

The flash control program then offers two options:
1. it can try to find the actual bytecode of the calibration routine in the hex file. If it finds it, it can write the calibration value and nop out the rest

2. it can't find the exact bytecode, but you can manually specify the calibration value address, nop start address and nop length.

The 2nd option allows the user to easily experiment with different calibration routines without having to change the flash control program each time.

One reason for a custom calibration routine that comes to mind would be calibration for two different vcc voltage levels, for example if the controller will be used with varying battery voltage.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on February 09, 2019, 11:46:35 pm
So I've a long time without time to spend on my programmer, I've finally had some to test the double software-controlled SEPIC DC-DC converters for feeding the PFS154.

Good thing is, the SEPIC design works perfectly fine. Bad thing is, the overly simplistic feedback loop I am using isn't really any good and many time it gets stuck oscillating while the PWM rate changes like mad. I guess I'll have to actually look at how PI loops work.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on February 10, 2019, 11:10:35 am
DC-DC converters tend to be hard to control when they have low/no load.

Try adding 100R dummy loads to each output.

Enviado de meu Moto MAXX usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 10, 2019, 02:58:12 pm
Hi,

I did some initial experiments with calibration of PFS154.

Here my measurements + notes:

1st experiment: Use PADAUK IDE, let WRITER calibrate the IC and then use our calibration loop and measure:

- .ADJUST_IC   SYSCLK=IHRC/2, IHRC=16MHz, VDD=5.0V;
- use IHRC 16MHz @ 5.0V @ 20°C
- SYSCLK = IHRC/2 => IC runs instructions @8 MHz (clkmd = 0x34, IDE calculated this value)
- our calibration loop toggles a pin on / off  within 8 clocks (7 instructions => 7 clocks + 1 extra clock from goto)
=> 1 MHz output on pin expected when measured with oscilloscope

measured: 1.0021 MHz - 1.0029 MHz  (slight temp up/down like put finger or blow over it: 1.0015 - 1.0036 MHz)

notes:
@7ED start val for IHRCR on PFS154: 0x80
@7EE start val for BGTR on PFS154: 0x5A
@7FE IHRCR value from WRITER: 0x81 (used for normal execution)


2nd experiment: Use PADAUK IDE, disable any calibration from WRITER and then use our calibration loop and measure:
- .ADJUST_IC DISABLE;
- use IHRC 16MHz @ 5.0V @ 20°C
- SYSCLK = IHRC/2 => IC runs instructions @8 MHz (clkmd = 0x34, IDE calculated this value)
- our calibration loop toggles a pin on / off  within 8 clocks (7 instructions => 7 clocks + 1 extra clock from goto)
=> 1 MHz output on pin expected when measured with oscilloscope

measured: 591.3 - 591.6 kHz  :-// :-// :-//

So it looks like we really need calibration or at least use the standard value of 0x80 for IHRCR on PFS154.

Unfortunately the PADAUK IDE does not allow to compile a program which sets IHRCR (error: "The 'IHRCR' not be supported at User Mode") so I'm stuck here.

=> Time to focus on the PC program to send data to easy pdk programmer for easy flashing of sdcc generated programs.


JS

UPDATE:

After some more experiments, the following IHRCR values for the specific PFS154 I try this with results in this values:

IHRCR
0x00 =>  591.4 kHz
...
0x80 =>  990.5 kHz
0x81 => 1002.5 kHz
...
0xFF => 1490.8 kHz


WOW, almost 1.5 MHz which translates to approx 12MHz sysclock (24MHz IHRC)  :) :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on February 10, 2019, 08:45:35 pm
Try adding 100R dummy loads to each output.
Thanks. I've tried it and it gets somewhat better, but still gets screwed every now and then. I guess I'll try that the PID controller.

Development is going slightly slow given my current limited debugging (literally doing single byte hex prints over serial) and lack of knowledge on the matter.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: GonzoTheGreat on February 13, 2019, 02:29:30 am
I had thought about getting an ATtiny261, running V-USB on it and have the smallest and simplest, all-DIP programmer.
Whay not use a Padauk MCU to program Padauk MCUs.
...+ some off-the shelf discrete components.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on February 13, 2019, 02:36:06 am
I am looking into an ESP8266 wifi enabled programmer. Check esplink for arduinos and ARMs.

I am usually terrified of direct copper to my expensive-ish computers while developing stuff that may blow up. :-)

Enviado de meu Moto MAXX usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ebclr on February 13, 2019, 03:43:02 am
This will help you on protecting your expensive pc

https://www.ebay.com/itm/USB-Isolator-for-Full-Speed-Built-in-DC-DC/122414725791?hash=item1c807c7a9f:g:dncAAOSwXYtY1g1A:rk:3:pf:0 (https://www.ebay.com/itm/USB-Isolator-for-Full-Speed-Built-in-DC-DC/122414725791?hash=item1c807c7a9f:g:dncAAOSwXYtY1g1A:rk:3:pf:0)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on February 14, 2019, 05:12:12 pm
I had thought about getting an ATtiny261, running V-USB on it and have the smallest and simplest, all-DIP programmer.
Whay not use a Padauk MCU to program Padauk MCUs.
...+ some off-the shelf discrete components.

It's an egg-and-chiken problem: I can't develop a programmer using a Padauk device if I can't get them programmed the first place  ;D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on February 16, 2019, 10:09:07 am
Well after seeing how hard was to get a SEPIC driver working, and specially, seeing how it didn't actually improve board size because of how large the inductors were, I've went back to a single boost converter using a series of transistors to switch where VDD is connected to. This time I've made the high side switch work properly.

Here's my current schematic:
(https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/?action=dlattach;attach=653775)

And this time, instead of wiring everything on a breadboard, I've decided to make a tiny prototype PCB:
(https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/?action=dlattach;attach=653781)

It turns out to be pretty small. It better be after five hours moving and adjusting components  |O

I'm a computer engineer, not an electronics engineer, so if anybody is able to spot any error, it'd be nice to let me know to fix it before ordering it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on February 17, 2019, 07:53:54 pm
I don't think it makes sense to build a boost converter yourself, except for fun and learning. There are so many ICs out there which does this, probably at lcsc.com for cheap as well, which need just one external inductor. The performance and regulation is probably better than your DIY version, and parts costs might be lower. And for each part, you would need to pay assembly cost too, if a manufacturer does the full board for you. Using a fixed voltage boost converter and a microcontroller with a DAC, and an OpAmp, would then be the easiest and most reliable way to regulate it, and with low noise and ripple.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on February 17, 2019, 08:42:07 pm
I don't think it makes sense to build a boost converter yourself, except for fun and learning. There are so many ICs out there which does this, probably at lcsc.com for cheap as well, which need just one external inductor. The performance and regulation is probably better than your DIY version, and parts costs might be lower. And for each part, you would need to pay assembly cost too, if a manufacturer does the full board for you. Using a fixed voltage boost converter and a microcontroller with a DAC, and an OpAmp, would then be the easiest and most reliable way to regulate it, and with low noise and ripple.
No matter which way I go, I still need one inductor, one diode and one capacitor for a boost converter. It is true that using a dedicated converter would simplify the boost converter design (by removing the MOSFET and the enable PNP and replacing that with a boost IC with input enable pin).

However, I would then need a way to reliably adjust the output voltage, by either making an array of feedback resistor dividers or by using that DAC+OpAmp configuration. The former needs several resistors, increasing the required board space, plus pins on the microcontroller that I don't have. The later would need another IC plus the charge pump JS has had to use on his design, which also means more parts and larger board.

Regarding regulation quality and noise, remember it's just a digital IC. So far using this design I've successfully programmed data on it using any voltage from 5.8 up to 6.2. Thus, it's not really sensitive and I'd be good to go with it.

Thus by any means I fail to see how using a dedicated boost controller would make things any easier, smaller, or cheaper.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on February 18, 2019, 01:00:54 am
Fresh baked PCBs.

Quad voltage source with DAC084S085 & ALM2402 x2
Quad level shifter with 74LVCH1T45 x4
PMS150C (13 bit)
PFS154  (14 bit)
PFS173  (15 bit)

Next step is to write some code and test the quad voltage source for stability, accuracy, and slew rate.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on February 28, 2019, 10:36:49 am
Evaluation boards (design on https://github.com/free-pdk/f-eval-boards), hand-soldered prototypes (well the PFS232 is not yet available from Padauk, so for that one Ihave the pcb only).

Left: PFS173
Middle: PFS154
Right: PFS232

One can't see it very well in the image, but the bottom header (for programming) has pin names below.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 28, 2019, 10:42:10 pm
Evaluation boards (design on https://github.com/free-pdk/f-eval-boards), hand-soldered prototypes).

Nice timing. I just got PCB1.2 revision of Easy PDK Programmer and soldered a small batch. No problems found so far. Everything working as expected.

Firmware for the STM32 is almost complete (I think next weekend I can finish last part of calibration).
Initial host software is also working (command line utility which supports Linux/Mac/Windows for reading/writing/executing + serial output debugging).

I will upload all schematics + firmware + software right after I'm sure everything is working as expected.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on March 01, 2019, 08:03:31 am
Quote
Nice timing. I just got PCB1.2 revision of Easy PDK Programmer and soldered a small batch. No problems found so far. Everything working as expected.

Firmware for the STM32 is almost complete (I think next weekend I can finish last part of calibration).
Initial host software is also working (command line utility which supports Linux/Mac/Windows for reading/writing/executing + serial output debugging).

I will upload all schematics + firmware + software right after I'm sure everything is working as expected.
That's great, because Also I have ordered some PFS173-S14, I hope they become useful in my projects! Also I found it weird, I can not find these puppies from my other Chinese suppliers! I have at list tried 10 different suppliers, I only got them from lcsc :(
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 01, 2019, 10:38:32 am
Firmware for the STM32 is almost complete (I think next weekend I can finish last part of calibration).
Initial host software is also working (command line utility which supports Linux/Mac/Windows for reading/writing/executing + serial output debugging).

Which Padauk devices are currently supported?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 01, 2019, 12:18:40 pm
Firmware for the STM32 is almost complete (I think next weekend I can finish last part of calibration).
Initial host software is also working (command line utility which supports Linux/Mac/Windows for reading/writing/executing + serial output debugging).

Which Padauk devices are currently supported?

Philipp

The firmware for STM32 is generic and should support any IC.
All parameters are defined and sent from the host software.

I focused on testing everything with PFS154 but support for other ICs can be added easily.

Here an example of one entry of the IC definition table in host software:

static const FPDKICDATA fpdk_ic_table[] =
{
  { .name               = "PFS154",
    .otpid              = 0x2AA1,
    .type               = FPDK_IC_FLASH,
    .addressbits        = 13,
    .codebits           = 14,
    .codewords          = 0x800,
    .ramsize            = 64,
    .exclude_code_start = 0x7ED, //use 0xFFFF to disable
    .exclude_code_end   = 0x7F0, //use 0xFFFF to disable
    .vdd_cmd            = 3.0,
    .vpp_cmd            = 5.6,
    .vdd_write          = 5.8,
    .vpp_write          = 8.5,
    .vdd_erase          = 5.8,
    .vpp_erase          = 8.5,
    .default_ihrcr      = 0x80,
    .default_bgtr       = 0x5A,
  },
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 06, 2019, 03:03:15 pm
Hi,

today I was very excited when I finally got the following output:

bash-3.2$ sdcc -mpdk14 hellopfs154noprintf.c


bash-3.2$ ./easypdkprog write hellopfs154noprintf.ihx --icname PFS154 --fuse 31FD
Erasing IC... done.
Writing IC... done.
Writing IC Fuse... done.


bash-3.2$ ./easypdkprog start
Running IC (5.00V)... IC started, press [Esc] to stop.
Hello World!
Hello World!
Hello World!
Hello World!


Explanation:
1. SDCC compiler development branch which supports PADAUK (MANY MANY thanks to SPTH and Nicolas Lesser) is used to compile a small test program

2. easypdkprog is used to send the compiled program to PFS154 sitting in a socket on top of the Easy PDK programmer

3. the PFS154 IC is started while still in the socket on top of the programmer. All serial output on PA.7 is captured and shown on the screen


So real development can start now  :)



I will cleanup the sources and release all of them on https://free-pdk.github.io during the next few days:
- Easy PDK programmer schematic and PCB design files
- STL files for 3D printable housing (housing not required)
- Easy PDK programmer firmware + source code
- easypdkprog source code

Right now only PFS154 is supported but other types will get added quickly now.

 :) :) :)


In case you are curious here the output of:

bash-3.2$ ./easypdkprog --help
Usage: easypdkprog [OPTION...] probe|read|write|erase|start [FILE]
easypdkprog -- read, write and execute programs on PADAUK microcontroller
https://free-pdk.github.io

  -b, --bin                  Binary file output. Default: ihex8
  -c, --calibrate            Calibrate IC after writing
  -f, --fuse=FUSE            FUSE value, e.g. 0x31FD
  -n, --icname=NAME          IC name, e.g. PFS154
      --noblankchk           Skip blank check before write
      --noerase              Skip erase before write
      --noverify             Skip verify after write
  -o, --otpid=ID             OTP ID, e.g. 0x2AA1
  -p, --port=PORT            COM port of programmer. Default: Auto search
  -r, --runvdd=VDD           VDD voltage for running IC (e.g. 3.3). Default: 5.0
  -v, --verbose              Verbose output
  -?, --help                 Give this help list
      --usage                Give a short usage message
  -V, --version              Print program version

Mandatory or optional arguments to long options are also mandatory or optional for any corresponding short options.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 07, 2019, 10:21:26 am
1. SDCC compiler development branch which supports PADAUK (MANY MANY thanks to SPTH and Nicolas Lesser) is used to compile a small test program

We've made quite some progress recently. It seems, there now is only one remaining bug to be fixed (related to arrays that are not const) to get the first of the SDCC regression tests (it tests abs() and labs() from the standard library) to pass.

I assume we can fix enough bugs to make four fifths or so of the tests pass sometime next week, which should be good enough to merge to trunk, so the pdk14 backend would make it into the next SDCC release (3.9.0).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 08, 2019, 03:28:16 pm
Where can we download latest SDCC?

Right now you have to go to the "pdk" branch of sdcc in their svn, check it out and compile it.

https://sourceforge.net/p/sdcc/code/HEAD/tree/branches/pdk/

But remember, it is an experimental branch which might or might not work from day to day (lot of activity right now).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 08, 2019, 07:10:45 pm
Quote from: js_12345678_55AA
...check it out and compile it.
Thank You. It's working.
https://www.youtube.com/watch?v=5b4hpZgaVnI (https://www.youtube.com/watch?v=5b4hpZgaVnI)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 10, 2019, 11:34:22 pm
Quote from: js_12345678_55AA
...check it out and compile it.
Thank You. It's working.

Do you plan to share your project / source / ... ?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 11, 2019, 12:12:59 pm
https://github.com/piotr-go/PADAUK

PFS154-S08 POV display: :)
(https://raw.githubusercontent.com/piotr-go/PADAUK/master/soft_pov/POV.JPG)
(https://raw.githubusercontent.com/piotr-go/PADAUK/master/foto_001.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 12, 2019, 01:37:34 pm
Yes really need the +1 for PCADD. Otherwise my program was jumping into nowhere, crashing (I think it adds 256 in the case of A=0, will need to investigate)

Any news on zero a?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 13, 2019, 12:10:37 am
Yes really need the +1 for PCADD. Otherwise my program was jumping into nowhere, crashing (I think it adds 256 in the case of A=0, will need to investigate)

Any news on zero a?

Philipp

I'm working on PFS173 support (read/erase is working, somehow write does not write a single bit yet).

PCADD A   with A=0:

Possibility 1:
The IC will do the equation mentioned in reference manual: "PC <- PC + A" which results in an endless loop.

Possibility 2:
PC is incremented by 1 automatically after each instruction. So maybe IC is subtracting 1 from operand and then adds this to the already advanced PC.
In case A=0 this subtraction would result in 0xFF which is added to the advanced PC which would be same as "PCADD 0x100"
This would match the behavior I observed when I tried it with ICE (I found program execution somewhere in code memory after "pcadd 0")... but this also could be an ICE bug.

In order to try this we would need to create and run a small test assembly program like this:


TEST_PCADD:
MOV A,0
PCADD A
RET 0x01
RET 0x02
...
RET 0xFE
RET 0xFF
RET 0x00

MAIN:
CALL TEST_PCADD
==> A holds result
if 0 then is variant 2
if not coming back then variant 1
if anything else then ??


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on March 13, 2019, 06:35:55 am
Quote
I'm working on PFS173 support (read/erase is working, somehow write does not write a single bit yet).
Thanks, I have orders some of these ;) :-[
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 14, 2019, 09:17:51 am
Quote
I'm working on PFS173 support (read/erase is working, somehow write does not write a single bit yet).
I have similar results with my programmer.
Different write command?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 14, 2019, 05:50:57 pm
The pdk branch of SDCC has been merged to trunk today. Further development will happen there.

From tomorrow, the nightly snapshots (http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)) should include support for pdk14 and pdk15.

The pdk14 port is working quite well now; while many regression tests had to be disabled ofr pdk14 due to lack of memory, the large number of tests passing still indicate that pdk14 is quite stable now:

Summary for 'pdk14': 10 failures, 2997 tests, 2101 test cases, 1463033 bytes, 17333727 ticks

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on March 14, 2019, 10:12:16 pm
Hi,

I will cleanup the sources and release all of them on https://free-pdk.github.io during the next few days:
- Easy PDK programmer schematic and PCB design files
Thanks for posting the hardware files of the programmer.

I was about to order the pcb and had a look at the Gerber_EASYPDKPROG_PCB12_Panel4x_NoSilk.zip file in a gerber viewer (gerbv from the gEDA project). I have attached a screenshot.

It looks like only one of the programmers is in the gerbers and not a panel of 4, 3 are empty. Also the plated slot for the usb connector looks just like a hole. So I'm a bit in doubt if these gerbers are correct. But there also might be some advanced gerber functions at play that gerbv doesn't understand.

Did you use these gerber files to order at JLCPCB or did you use a direct order link from easyeda into JLCPCB?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 15, 2019, 12:06:57 pm
Did you use these gerber files to order at JLCPCB or did you use a direct order link from easyeda into JLCPCB?

The exact same Gerber ZIP file was uploaded to JLCPCB using the upload Gerber function. The production went smoothly and the received PCB panels did not have any error (also the USB port fits nicely).

The multiple copy of the outline without having the same PCB inside is an industry standard for PCB factories used to indicate to panelize the PCB.


In case you plan to build the programmer please consider clicking on the AFFILIATE link when you start to order parts of the BOM on lcsc web site: LCSC.com (https://lcsc.com?s_url=DWfnXH)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on March 15, 2019, 01:47:14 pm
The exact same Gerber ZIP file was uploaded to JLCPCB using the upload Gerber function. The production went smoothly and the received PCB panels did not have any error (also the USB port fits nicely).
Good to know, thanks.

The multiple copy of the outline without having the same PCB inside is an industry standard for PCB factories used to indicate to panelize the PCB.
I never heard of that one. All the tutorials regarding panelization I've seen copy the actual content. Do you happen to have a link or document explaining the details of this process?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: anxzhu on March 15, 2019, 02:15:03 pm
https://docs.easyeda.com/en/PCB/Panelize/index.html
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 15, 2019, 04:48:53 pm
Do we have any idea which devices support ldsptl or ldspth, and which ones don't?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on March 15, 2019, 05:06:20 pm
Only supported by the 14 bit parts.

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2010509/#msg2010509 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2010509/#msg2010509)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 15, 2019, 05:53:45 pm
Only supported by the 14 bit parts.

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2010509/#msg2010509 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2010509/#msg2010509)

More correct: PADAUK IDE generates opcodes only for 14 bit parts.

However they might be in all processor variants.

Another example for this assumption: 15 bit devices reference 4 opcodes in manual which IDE also does not compile:

NMOV A, M
NMOV M, A
SWAP M
XOR A, IO

But there is space inside of the instruction set to support exact this opcodes.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 19, 2019, 05:50:26 pm
Quote
I'm working on PFS173 support (read/erase is working, somehow write does not write a single bit yet).
Any progress?

I think i found a new command.
0xA5A5A5AB, with B like BRICKED at the end ;D
When executed µC looks like locked, but FW does not work and cannot be erased.
Tested on pfs154 and pfs173, vpp 10V, vcc 5V/6V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 19, 2019, 07:59:56 pm
Quote
I'm working on PFS173 support (read/erase is working, somehow write does not write a single bit yet).
Any progress?

I think i found a new command.
0xA5A5A5AB, with B like BRICKED at the end ;D
When executed µC looks like locked, but FW does not work and cannot be erased.
Tested on pfs154 and pfs173, vpp 10V, vcc 5V/6V.

I got PFS154 and PFS173 working, now focusing on OTP like PMS154 / B / C.

./easypdkprog list
Supported ICs:
 PMS154   (0xA06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PFS154   (0xAA1): FLASH: 2048 (14 bit), RAM: 128 bytes
 PMS154B  (0xC06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS154C  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PFS173   (0xEA2): FLASH: 3072 (15 bit), RAM: 256 bytes


After this only internal high/low speed osc (IHRCR / ILRCR) and bandgap (BGTR) tuning is left to do.

So release of firmware / host software is coming soon :-)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 19, 2019, 08:06:51 pm
What's the difference beetween PFS154 and PFS173 in write?

A5A5A5A7
1 bit
15 bit word
15 bit word
15 bit word
15 bit word
13 bit address
...
...

?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 19, 2019, 10:51:01 pm
What's the difference beetween PFS154 and PFS173 in write?

A5A5A5A7
1 bit
15 bit word
15 bit word
15 bit word
15 bit word
13 bit address
...
...

?

The difference is only 4x15 bit (PFS173) instead of 4x14 bit (PFS154). Address is 13 bit for both. Slow clocks after address is 4 cycles for both on my programmer (on original WRITER it used 8 slow clocks for PFS173).
In High-Voltage phase VDD is 5.6V and VPP 8.0V for write. Erase uses VDD 2.0V or 3.0V and VPP 9.0V in high voltage phase.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on March 20, 2019, 10:43:33 am
Now it's working.
I had too high VDD.
It worked on pfs154 and pms150c but not pfs173.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: anxzhu on March 24, 2019, 02:55:19 am
 :-+ :-+ :-+Firmware please
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 26, 2019, 12:05:32 am
:-+ :-+ :-+Firmware please

Software / firmware will come soon.

OTP support is working now.

The following ICs are fully tested and supported by easypdkprog right now:

./easypdkprog list
Supported ICs:
 PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes
 PFS154   (0xAA1): FLASH: 2048 (14 bit), RAM: 128 bytes
 PMS154B  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS154C  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PFS173   (0xEA2): FLASH: 3072 (15 bit), RAM: 256 bytes


(more to come)

Calibration is 80% done, automatic search, insertion, execution and removing (with NOP) of calibration function is working already.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on March 26, 2019, 05:56:56 am
Thumbs up JS   :-+ :-+ :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 29, 2019, 02:20:42 pm
Hi,

I got distracted a bit  :) after I saw a youtube video from bigclive.com where he found another small gadget which most likely contains a PADAUK IC (he mentioned it in his video).

Video: https://www.youtube.com/watch?v=xY7Rc10U3Cg (https://www.youtube.com/watch?v=xY7Rc10U3Cg)

Item: https://www.ebay.com/itm/182936210709 (https://www.ebay.com/itm/182936210709)


I went and bought some. After they arrived I removed the IC with hot air and placed it in Easy PDK programmer:

Surprise surprise...

./easypdkprog probe
TYPE:OTP RSP:0x285A0 VPP=4.50 VDD=2.00
IC is supported: PMS150C ICID:0xA16

 
OK, it is a PMC150C !!!

Next step:

./easypdkprog -n PMS150C read test.bin -b
Reading IC... done.


Great! But wait... dump looks a bit strange:

./hexdump test.bin
0000000 29 18 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000010 ff 1f 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000020 32 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000030 25 09 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000040 33 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000050 24 18 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000060 b1 18 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000070 40 17 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000080 c2 07 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0000090 90 0d 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00000a0 02 04 00 00 00 00 00 00 00 00 00 00 00 00 00 00
...
00007a0 ff 1f 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00007b0 ff 1f 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00007c0 ff 1f 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00007d0 ff 1f 00 00 00 00 00 00 00 00 00 00 00 00 00 00
00007e0 ff 1f ff 1f ff 1f ff 1f ff 1f ff 1f ca 01 ff 1f
00007f0 24 07 cc 1f ff 1f ff 1f ff 0f ff 1f 5a 01 fc 02


It looks like some sort of security prevents us from reading the complete content.
However the read seems to work good since we see the complete reserved area at the end.

==> Let's have a look at the "last word" (FUSE), it is 0x02FC

Let's have a look at the IC datasheet / IDE include files / ...

in PMS150C.INC we can find:
   .Assembly   OPTION   0   Security   Enable   Disable
   .Assembly   OPTION   2   LVR   4.0V   3.5V   3.0V   2.75V   2.5V   1.8V   2.2V   2.0V
   .Assembly   OPTION   7   Drive      Low   Normal
   .Assembly   OPTION   10   Bootup_Time   Slow   X   X   Fast
   .Assembly   OPTION_LOW   1, 8, 12 ~ 15
   .Assembly   OPTION_DEFAULT   0x02FC



==> 0x2FC is the default with security enabled

However the Option_Help for Security reads like this
  Enable  : "Security 7/8 words Enable"
  Disable : "Security Disable"


Hmmm... "Security 7/8 words Enable", looks exactly like our dump.
==> 7 out of 8 words are security enabled (will read all 0 when reading the IC)

So what now? Is this the end?

Of course not!

- as we can see, the first instruction is 0x1829 which translates to "GOTO 0x29".
  (IDE always creates a JUMP to FPPA0 function as first instruction for PMC150)
- after this jump some space is unused (multi core PADAUK devices insert the startup jump for the other cores there)
- at 0x20 the interrupt service routine starts (fixed location for PMC150)
- at the end of the IC code memory we can see a lot of 0x1FFF, so most likely this space is unused as well


==> What if:
- we overwrite the first instruction with all 0 (NOP)
- place a jump to the near end of code memory at instruction 1
- write a special small program near the end of code memory which uses LDSPTL/LDSPTH to read code memory and send it out via GPIO


After some fiddeling and dry runs with fresh IC I got the following:

./easypdkprog -n PMS150C write dump_150c_ovl.hex --noblankchk --noverify
Writing IC... done.


Then I started the IC and got data from it:

./hexdump cardoorlight_dumped.bin
0000000 00 00 d0 1b ff 1f ff 1f ff 1f ff 1f ff 1f ff 1f
0000010 ff 1f ff 1f ff 1f ff 1f ff 1f ff 1f ff 1f ff 1f
0000020 32 00 45 0d 1b 18 45 0e 20 09 62 02 23 09 82 02
0000030 25 09 e2 02 22 09 f5 17 d0 05 58 17 d1 05 d0 00
0000040 33 00 3b 00 64 17 e6 05 e6 07 00 0c 3a 00 66 09
0000050 24 18 30 00 3a 17 82 00 f6 1f 99 00 fe 1f ff 12
0000060 b1 18 d1 0f 40 17 8b 00 1c 17 83 00 06 17 c6 05
0000070 40 17 c1 05 8b 00 c0 09 c7 05 81 0a 01 08 06 09
0000080 c2 07 c4 05 c3 07 c5 05 01 17 c2 05 83 09 03 17
0000090 90 0d 48 18 d0 0f 90 0d 59 18 02 09 90 0d 59 18
00000a0 02 04 90 0d 57 18 03 08 90 0c 4b 18 58 18 42 09
...


:) :) :)

What do we learn from this?

=> do not leave empty space in IC when you want to prevent a readout.

=> IDE provides a simple method for this (mentioned in user manual):
  .Fill_Space     RESET;
or
  .Fill_Space     NOP;

=> I will add an option for Easy PDK programmer to set unused space to 0 (NOP)

=> and WTF is 7/8 security???


Best part: This product is a cheap source for 2x PCB + battery holder + housing + battery + magnet (pcb magnet sensor + 3x led for own projects) :)


Have fun,

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lucas.hartmann on March 29, 2019, 02:48:45 pm
Even if all empty space was filled, maybe you can side channel attack the programming cycle. I remember that previously you guys had only a few bits programming due to limited power supply...

Try writing 0 to one bit at a time and record the programming current.

I am assuming programming a previously 1 bit takes more energy than a previously 0 bit. If it works then there is no more code protection viable for these IC.

Enviado de meu Moto MAXX usando o Tapatalk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 29, 2019, 05:11:12 pm
Even if all empty space was filled, maybe you can side channel attack the programming cycle. I remember that previously you guys had only a few bits programming due to limited power supply...
Try writing 0 to one bit at a time and record the programming current.
I am assuming programming a previously 1 bit takes more energy than a previously 0 bit.

This was plan B..., however plan A worked like a charm.
The difference between writing 0=>0 and 1=>0 is clearly visible on oscilloscope. But on VDD and not on VPP like you would assume.
That's why ADC is connected to both VPP and VDD in Easy PDK programmer  ;).

If it works then there is no more code protection viable for these IC.
This is a *cheap* IC, not a security IC. It also costs next to nothing sending PADAUK IC to the usual suspects for IC extraction.
JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 01, 2019, 10:26:24 am
Calibration seems to work nice  :) :) :)

$ make flash run
sdcc -lpdk14 -mpdk14 -c hellopfs154.c -o hellopfs154.rel
sdcc -lpdk14 -mpdk14 --out-fmt-ihx hellopfs154.rel -o hellopfs154.hex

easypdkprog --icname=PFS154 write hellopfs154.hex
Erasing IC... done.
Writing IC... done.
Calibrating IC (@4.00V IHRC SYSCLK=8000000Hz)... calibration result: 7995368Hz (0x81)  done.

easypdkprog start
Running IC (4.00V)... IC started, press [Esc] to stop.
Hello World!
Hello World!
Hello World!
Hello World!
Hello World!

IC stopped


Above you see: compilation with SDCC, writing + calibration with Easy PDK programmer, executing the program while IC is still in Easy PDK programmer socket, UART with autobaud receives from /sends to IC.


I also found out something new: OTP area inside of flash based PADAUK ICs
(I think it is still flash but a flag tells IC to not erase this section(s) anymore)
==> Dangerous! I did not find any way to change this values back. So once it is declared as OTP and written it stays there!

Both flash based ICs from PADAUK (PFS154 / PFS173) seem to have a default small OTP area (factory tuning data is stored inside).
It also looks like a 3rd value holds flags to (re)define more parts of IC as OTP:
- PFS154: @0x7E0 - 0x7EF  standard OTP area
- PFS173: @0xBE0 - 0xBEF  standard OTP area

@0x7E0 / 0xBE0 = <unused OTP, can be used for user data storage>
@0x7E1 / 0xBE1 = <unused OTP, can be used for user data storage>
...
@0x7EC / 0xBEC = <unused OTP, can be used for user data storage>
@0x7ED / 0xBED = factory IHRCR tuning value
@0x7EE / 0xBEE = factory BGTR tuning value
@0x7EF / 0xBEF = not 100% analyzed: value / bit mask setting OTP state for flash pages, when is all 0 then complete IC can not be erased / written? anymore



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 02, 2019, 09:15:43 am
Hi,

I'm hunting unknown opcodes (PDK15 is mentioning NMOV A, M / NMOV M, A / SWAP M  in documentation but IDE has a bug not implementing them).

In order to do this I wrote a simple fuzzer (nothing sophisticated, just a start).

Code: [Select]
volatile unsigned char mem, ta, ra, rf, rsp;

...

  ra=0;
  rf=0;
  rsp=0;
  for(ta=0;;ta++)
  {
    putchar('T'); printhex(ta); putchar('-');

    __asm
      mov a, #0
      mov __flag, a
      mov a, _ta
   
      .dw 0x0064         //instruction opcode
   
      mov _ra, a
      mov a, __flag
      mov _rf, a
      mov a, __sp
      mov _rsp, a
    __endasm;

    putchar('a');printhex(ra); putchar('-'); 
    putchar('f');printhex(rf); putchar('-');
    putchar('s');printhex(rsp); putchar('-');
    putchar('m');printhex(mem);.
    putchar('\n');
    for(unsigned long int i=10000; i>0; i--); // Wait approx. 20ms
  }
 
...


Basically it is a loop loading different values to the A register then executing the opcode and then it outputs changes to A, flags, stack pointer or memory (only monitoring RAM address 0)

I made a quick test with PFS154 and found the following:

- every opcode I tried executed and the processor was still running afterwards (no lockups on unused instructions)

- most unknown instructions seem to execute as NOP (more tests needed)

- one new undocumented opcode was found for PFS154:  :)
Opcode 0x0064:
Code: [Select]
T00-a00-fF1-s10-m00
T01-aFF-fF6-s10-m00
T02-aFE-fF6-s10-m00
T03-aFD-fF6-s10-m00
T04-aFC-fF6-s10-m00
T05-aFB-fF6-s10-m00
T06-aFA-fF6-s10-m00
T07-aF9-fF6-s10-m00
T08-aF8-fF6-s10-m00
T09-aF7-fF6-s10-m00
T0A-aF6-fF6-s10-m00
T0B-aF5-fF6-s10-m00
T0C-aF4-fF6-s10-m00
T0D-aF3-fF6-s10-m00
T0E-aF2-fF6-s10-m00
T0F-aF1-fF6-s10-m00
T10-aF0-fF2-s10-m00
T11-aEF-fF6-s10-m00
T12-aEE-fF6-s10-m00
T13-aED-fF6-s10-m00
T14-aEC-fF6-s10-m00
T15-aEB-fF6-s10-m00
T16-aEA-fF6-s10-m00
T17-aE9-fF6-s10-m00
T18-aE8-fF6-s10-m00
T19-aE7-fF6-s10-m00
T1A-aE6-fF6-s10-m00
T1B-aE5-fF6-s10-m00
T1C-aE4-fF6-s10-m00
T1D-aE3-fF6-s10-m00
T1E-aE2-fF6-s10-m00
T1F-aE1-fF6-s10-m00
T20-aE0-fF2-s10-m00
T21-aDF-fF6-s10-m00
T22-aDE-fF6-s10-m00
T23-aDD-fF6-s10-m00
T24-aDC-fF6-s10-m00
T25-aDB-fF6-s10-m00
T26-aDA-fF6-s10-m00
T27-aD9-fF6-s10-m00
T28-aD8-fF6-s10-m00
T29-aD7-fF6-s10-m00
T2A-aD6-fF6-s10-m00
T2B-aD5-fF6-s10-m00
T2C-aD4-fF6-s10-m00
T2D-aD3-fF6-s10-m00
T2E-aD2-fF6-s10-m00
T2F-aD1-fF6-s10-m00
T30-aD0-fF2-s10-m00
T31-aCF-fF6-s10-m00
T32-aCE-fF6-s10-m00
T33-aCD-fF6-s10-m00
T34-aCC-fF6-s10-m00
T35-aCB-fF6-s10-m00
T36-aCA-fF6-s10-m00
T37-aC9-fF6-s10-m00
T38-aC8-fF6-s10-m00
T39-aC7-fF6-s10-m00
T3A-aC6-fF6-s10-m00
T3B-aC5-fF6-s10-m00
T3C-aC4-fF6-s10-m00
T3D-aC3-fF6-s10-m00
T3E-aC2-fF6-s10-m00
T3F-aC1-fF6-s10-m00
T40-aC0-fF2-s10-m00
T41-aBF-fF6-s10-m00
T42-aBE-fF6-s10-m00
T43-aBD-fF6-s10-m00
T44-aBC-fF6-s10-m00
T45-aBB-fF6-s10-m00
T46-aBA-fF6-s10-m00
T47-aB9-fF6-s10-m00
T48-aB8-fF6-s10-m00
T49-aB7-fF6-s10-m00
T4A-aB6-fF6-s10-m00
T4B-aB5-fF6-s10-m00
T4C-aB4-fF6-s10-m00
T4D-aB3-fF6-s10-m00
T4E-aB2-fF6-s10-m00
T4F-aB1-fF6-s10-m00
T50-aB0-fF2-s10-m00
T51-aAF-fF6-s10-m00
T52-aAE-fF6-s10-m00
T53-aAD-fF6-s10-m00
T54-aAC-fF6-s10-m00
T55-aAB-fF6-s10-m00
T56-aAA-fF6-s10-m00
T57-aA9-fF6-s10-m00
T58-aA8-fF6-s10-m00
T59-aA7-fF6-s10-m00
T5A-aA6-fF6-s10-m00
T5B-aA5-fF6-s10-m00
T5C-aA4-fF6-s10-m00
T5D-aA3-fF6-s10-m00
T5E-aA2-fF6-s10-m00
T5F-aA1-fF6-s10-m00
T60-aA0-fF2-s10-m00
T61-a9F-fF6-s10-m00
T62-a9E-fF6-s10-m00
T63-a9D-fF6-s10-m00
T64-a9C-fF6-s10-m00
T65-a9B-fF6-s10-m00
T66-a9A-fF6-s10-m00
T67-a99-fF6-s10-m00
T68-a98-fF6-s10-m00
T69-a97-fF6-s10-m00
T6A-a96-fF6-s10-m00
T6B-a95-fF6-s10-m00
T6C-a94-fF6-s10-m00
T6D-a93-fF6-s10-m00
T6E-a92-fF6-s10-m00
T6F-a91-fF6-s10-m00
T70-a90-fF2-s10-m00
T71-a8F-fF6-s10-m00
T72-a8E-fF6-s10-m00
T73-a8D-fF6-s10-m00
T74-a8C-fF6-s10-m00
T75-a8B-fF6-s10-m00
T76-a8A-fF6-s10-m00
T77-a89-fF6-s10-m00
T78-a88-fF6-s10-m00
T79-a87-fF6-s10-m00
T7A-a86-fF6-s10-m00
T7B-a85-fF6-s10-m00
T7C-a84-fF6-s10-m00
T7D-a83-fF6-s10-m00
T7E-a82-fF6-s10-m00
T7F-a81-fF6-s10-m00
T80-a80-fFA-s10-m00
T81-a7F-fF6-s10-m00
T82-a7E-fF6-s10-m00
T83-a7D-fF6-s10-m00
T84-a7C-fF6-s10-m00
T85-a7B-fF6-s10-m00
T86-a7A-fF6-s10-m00
T87-a79-fF6-s10-m00
T88-a78-fF6-s10-m00
T89-a77-fF6-s10-m00
T8A-a76-fF6-s10-m00
T8B-a75-fF6-s10-m00
T8C-a74-fF6-s10-m00
T8D-a73-fF6-s10-m00
T8E-a72-fF6-s10-m00
T8F-a71-fF6-s10-m00
T90-a70-fF2-s10-m00
T91-a6F-fF6-s10-m00
T92-a6E-fF6-s10-m00
T93-a6D-fF6-s10-m00
T94-a6C-fF6-s10-m00
T95-a6B-fF6-s10-m00
T96-a6A-fF6-s10-m00
T97-a69-fF6-s10-m00
T98-a68-fF6-s10-m00
T99-a67-fF6-s10-m00
T9A-a66-fF6-s10-m00
T9B-a65-fF6-s10-m00
T9C-a64-fF6-s10-m00
T9D-a63-fF6-s10-m00
T9E-a62-fF6-s10-m00
T9F-a61-fF6-s10-m00
TA0-a60-fF2-s10-m00
TA1-a5F-fF6-s10-m00
TA2-a5E-fF6-s10-m00
TA3-a5D-fF6-s10-m00
TA4-a5C-fF6-s10-m00
TA5-a5B-fF6-s10-m00
TA6-a5A-fF6-s10-m00
TA7-a59-fF6-s10-m00
TA8-a58-fF6-s10-m00
TA9-a57-fF6-s10-m00
TAA-a56-fF6-s10-m00
TAB-a55-fF6-s10-m00
TAC-a54-fF6-s10-m00
TAD-a53-fF6-s10-m00
TAE-a52-fF6-s10-m00
TAF-a51-fF6-s10-m00
TB0-a50-fF2-s10-m00
TB1-a4F-fF6-s10-m00
TB2-a4E-fF6-s10-m00
TB3-a4D-fF6-s10-m00
TB4-a4C-fF6-s10-m00
TB5-a4B-fF6-s10-m00
TB6-a4A-fF6-s10-m00
TB7-a49-fF6-s10-m00
TB8-a48-fF6-s10-m00
TB9-a47-fF6-s10-m00
TBA-a46-fF6-s10-m00
TBB-a45-fF6-s10-m00
TBC-a44-fF6-s10-m00
TBD-a43-fF6-s10-m00
TBE-a42-fF6-s10-m00
TBF-a41-fF6-s10-m00
TC0-a40-fF2-s10-m00
TC1-a3F-fF6-s10-m00
TC2-a3E-fF6-s10-m00
TC3-a3D-fF6-s10-m00
TC4-a3C-fF6-s10-m00
TC5-a3B-fF6-s10-m00
TC6-a3A-fF6-s10-m00
TC7-a39-fF6-s10-m00
TC8-a38-fF6-s10-m00
TC9-a37-fF6-s10-m00
TCA-a36-fF6-s10-m00
TCB-a35-fF6-s10-m00
TCC-a34-fF6-s10-m00
TCD-a33-fF6-s10-m00
TCE-a32-fF6-s10-m00
TCF-a31-fF6-s10-m00
TD0-a30-fF2-s10-m00
TD1-a2F-fF6-s10-m00
TD2-a2E-fF6-s10-m00
TD3-a2D-fF6-s10-m00
TD4-a2C-fF6-s10-m00
TD5-a2B-fF6-s10-m00
TD6-a2A-fF6-s10-m00
TD7-a29-fF6-s10-m00
TD8-a28-fF6-s10-m00
TD9-a27-fF6-s10-m00
TDA-a26-fF6-s10-m00
TDB-a25-fF6-s10-m00
TDC-a24-fF6-s10-m00
TDD-a23-fF6-s10-m00
TDE-a22-fF6-s10-m00
TDF-a21-fF6-s10-m00
TE0-a20-fF2-s10-m00
TE1-a1F-fF6-s10-m00
TE2-a1E-fF6-s10-m00
TE3-a1D-fF6-s10-m00
TE4-a1C-fF6-s10-m00
TE5-a1B-fF6-s10-m00
TE6-a1A-fF6-s10-m00
TE7-a19-fF6-s10-m00
TE8-a18-fF6-s10-m00
TE9-a17-fF6-s10-m00
TEA-a16-fF6-s10-m00
TEB-a15-fF6-s10-m00
TEC-a14-fF6-s10-m00
TED-a13-fF6-s10-m00
TEE-a12-fF6-s10-m00
TEF-a11-fF6-s10-m00
TF0-a10-fF2-s10-m00
TF1-a0F-fF6-s10-m00
TF2-a0E-fF6-s10-m00
TF3-a0D-fF6-s10-m00
TF4-a0C-fF6-s10-m00
TF5-a0B-fF6-s10-m00
TF6-a0A-fF6-s10-m00
TF7-a09-fF6-s10-m00
TF8-a08-fF6-s10-m00
TF9-a07-fF6-s10-m00
TFA-a06-fF6-s10-m00
TFB-a05-fF6-s10-m00
TFC-a04-fF6-s10-m00
TFD-a03-fF6-s10-m00
TFE-a02-fF6-s10-m00
TFF-a01-fF6-s10-m00


It reads as follows:
T00-a00-fF1-s10-m00
 Test input A = 0x00
 output a = 0x00
 output flags = 0xF1 (ZF)
 output stack = 0x10 (no change to stack)
 output mem0 = 0x00 (no change to memory address 0)

T01-aFF-fF6-s10-m00
 Test input A = 0x01
 output a = 0xFF
 output flags = 0xF6 (AC / CF)
 output stack = 0x10 (no change to stack)
 output mem0 = 0x00 (no change to memory address 0)

T10-aF0-fF2-s10-m00
 Test input A = 0x10
 output a = 0xF0
 output flags = 0xF2 (CF)
 output stack = 0x10 (no change to stack)
 output mem0 = 0x00 (no change to memory address 0)


This is clearly a NEG A instruction  (A=NEG A), it just behaves different from standard NEG A instruction in setting flags. Maybe a BCD capable NEG?



I'm waiting for the PDK15 assembler from SDCC to be ready to compile for PFS173 so we can hunt for the missing instructions there.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 03, 2019, 07:17:25 pm
I'm waiting for the PDK15 assembler from SDCC to be ready to compile for PFS173 so we can hunt for the missing instructions there.

The issues you reported are now fixed in the pdk branch.

Due to the upcoming 3.9.0 release, SDCC is currently in code freeze, so applying the fixes to trunk needs to be discussed on the developer list first, but I'm optimistic about them going in before RC1.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 05, 2019, 08:07:33 pm
Just a quick update on the state of Padauk support in the Small Device C Compiler:

pdk13: In development. Still in an early stage, but simple programs should mostly work. Currently to be found in the pdk branch only, won't make it into the 3.9.0 release in April.
pdk14: Stable (i.e. regression tests pass). Will be in SDCC 3.9.0.
pdk15: In development, but improving rapidly (>90% of regression tests pass). Will be in SDCC 3.9.0.
pdk16: Work has not yet begun (except for some preliminary evaluations).

We have a working simulator of the PMS132B and PMS134 (cores only so far, no peripherals) that is used for the regression testing.

The pdk branch (necesary for those that wnat to have a look at pdk13 support) can be found at
https://sourceforge.net/p/sdcc/code/HEAD/tree/branches/pdk/ (https://sourceforge.net/p/sdcc/code/HEAD/tree/branches/pdk/)
It also has some new features for pdk14 and pdk15 that are not yet in SDCC trunk.

For SDCC trunk, snapshots (including binaries) can be found at:
http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)

For those that want to use an IDE, I'd recommend Code::Blocks, since it has some SDCC support out-of-the-box.

Philipp

P.S.:

Plan for 2019:
* SDCC 3.9.0 release in April.
* Support PMC153 core in simulator
* Make the pdk15 backend stable
* Make the pdk13 backend work well for simple programs
* Support timers and interrupts in simulator
* Various small improvements to the generated code (in code generation, register allocation, peephole optimization)
* Another SDCC release near the end of the year.

Long-term plan:
* Various optimizations (in particular to reduce RAM usage and code size)
* Make the pdk13 backend stable
* Support pdk16 (assembler, linker, simulator, compiler)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 06, 2019, 09:04:33 pm
Hi,

finally... I found the time to prepare the first release of the Easy PDK programmer software:

https://github.com/free-pdk/easy-pdk-programmer-software

The firmware for the programmer is included as compiled BIN file right now. I just need a bit more time to clean it up and make it usable with a complete FOSS tool chain.
UPDATE: The firmware is included as compiled BIN file and with full source code.

Have fun,

JS


Update: I created a compiled executable for Windows user and attached it to the release: https://github.com/free-pdk/easy-pdk-programmer-software/releases/tag/1.0 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on April 07, 2019, 05:38:10 am
Thanks JS :-+ :-+ :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 08, 2019, 08:36:28 pm
Dear SDCC users,

Today the first Release Candidate (RC1) for SDCC 3.9.0 has been created.
As always it has been put online in our SourceForge File section.
https://sourceforge.net/projects/sdcc/files/

If you have the time, please verify it and report back with the positive
or negative results.

There have been various improvements, both features and bug fixes
since SDCC 3.8.0. The full ChangeLog is at
https://sourceforge.net/p/sdcc/code/HEAD/tree/tags/sdcc-3.9.0-pre1/sdcc/ChangeLog.

The following is a list of particularly noticeable new features.

* Support for struct / union assignment.
* Optimizations in the stm8 backend relevant to soft float increase Whetstone score by two thirds.
* Improvements in rematerialization in the stm8 backend improve code generation for struct, union and arrays.
* New stack allocator reduces stack space usage for the stm8, z80, z180, gbz80, r2k, r3ka, tlcs90 backends.
* New ez80_z80 backend for eZ80 in Z80 mode.
* Removed deprecated sdcclib utility.
* New pdk14 backend for Padauk µC with 14-bit wide program memory.
* New in-development pdk15 backend for Padauk µC with 15-bit wide program memory.

Philipp Klaus Krause
SDCC 3.9.0 Release Manager

P.S.: There currently is a survey on use of various SDCC backends:

https://terminplaner4.dfn.de/xudoK5vzYi3oIX6O

If you would like to see support in SDCC for a device not yet supported or if you use the mcs51 backend for a device that has support for dual dptr, please state so (and which device it is) in a comment.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 16, 2019, 06:52:42 am
SDCC 3.9.0 has been released yesterday; I also submitted the news to Slashdot (https://slashdot.org/submission/9526188/small-device-c-compiler-390-released).

Current state of Padauk support:
* pdk14 is stable (included in release)
* pdk15 will soon be stable (included in release, very few remaining regression failures)
* pdk13 is experimental (currently in pdk branch only, but will probably be merged to trunk soon)

pdk13 probably won't be considered stable anytime soon (it would need to pass regression tests, but we'd need better optimizations to reduce memory usage first, as currently, the test framework won't fit into the limited memory of 1 KW / 64 B).
pdk16 support is still far away (there are still open questions about how to properly support this multicore architecture in SDCC).

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 17, 2019, 01:57:13 pm
Hi,

I compiled list of IC types which can be physically piugged in Easy PDK Programmer directly by just using a SOP socket:

PMS15A-S08

PMC131-S16A
PMS131-S16A
PMC131-S14
PMS131-S14

PMS132-S16A
PMS132B-S16A
PMS132-S14
PMS132B-S14

PMS133-S16A
PMS134-S16A
PMS133-S16B
PMS134-S16B
PMS133-S14
PMS134-S14

PMC150-S08
PMS150-S08

PMS150C-S08 (supported)

PMS152-S16
PMS152-S14
PMS152-M10
PMS152-S08

PMC153-S14
PMS153-S14
PMC153-S08
PMS153-S08

PMS154B-S16 (supported)
PMS154B-S14 (supported)
PMS154B-M10 (supported)
PMS154B-S08 (supported)

PMS154C-S16 (supported)
PMS154C-S14 (supported)
PMS154C-M10 (supported)
PMS154C-S08 (supported)

PFS154-S16 (supported)
PFS154-S14 (supported)
PFS154-M10 (supported)
PFS154-S08 (supported)

PMS171B-S16
PMS171B-S14
PMS171B-M10
PMS171B-S08

PFS173-S16 (supported)
PFS173-S14 (supported)
PFS173-M10 (supported)
PFS173-S08 (supported)

PMC251-S14


All other types / variants will need the use of jumper wires between Easy PDK programmer and socket or an explicit adapter pcb.

Which types from the list above do you think are most interesting to support or what other types + adapter you would consider useful?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on April 17, 2019, 07:41:04 pm
I already created adapter pcbs for PMS150C-U06 and PFS154-U06 as I'm mostly interested in the SOT23-6 packages. I took the gerbers of your programmer pcb and added my adapters to it with a gerber panelizer. I planned to publish the Kicad sources & Gerbers on github when I received the pcbs and had a chance to test them. But I haven't received them yet, they are still in transit.

I attached a picture of the pcb panel.

It is intended to work like this:
The pins of my SOT23-6 adapters have the same pitch as the programmer pcb. So one adapter pcb is not enough as the pins would interfere.
So you solder pin headers to the lower adapter pcb (the one with just one white break-line) and put them into the programmer.
You solder pin headers to the outer rows of it and then one of the top adapter pcbs on top.

I created one for PMS150C-U06 and one for PFS154-U06. The one with the three white break-lines is intended as universal or manual adapter pcb. The white lines indicate breaks in the connections. So you can cross the outer two white lines with your own small jumper wires or similar to create the wanted connections.

If someone wants the files untested, I could also publish them now.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on April 18, 2019, 05:29:37 am
Thanks JS, I think the ones that have ADC is the first obvious choices, tough you have already PFS173 in the list, but I would go for 12 bit ADC versions too.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 19, 2019, 05:59:39 am

Which types from the list above do you think are most interesting to support or what other types + adapter you would consider useful?

JS

From an SDCC perspective, I'd currently consider the following the most interesting:

* PMS15A - since it is the very low-end device (and we now have a pdk13 backend supporting it - in current trunk and snapshots, but not the 3.9.0 release)

* PMS153 - this is the pdk13 type we have an emulator for, which was used for the (very little) testing done on the pdk13 backend.
* PMS132B - this is the pdk14 type we have an emulator for, which is also used for testing the pdk14 backend.
* PMS134 - this is the pdk15 type we have an emulator for, which is also used for testing the pdk15 backend.

* PFS172 - this will be the second flash pdk14 type; it is to be released this quarter.
* PFS232 - this will be the first dual-core flash device.

Currently, the emulators only emulator the core, but AFAIK, Nicolas is working on adding timer / interrupt support.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on April 19, 2019, 02:52:07 pm
I"m personally interested in the PMS-150C-U06 and PMS-15A-U06.

Thanks to all of you -- wonderful feat of reverse engineering you all accomplished there!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cnlohr on April 30, 2019, 04:18:07 pm
Oh man, this is amazing.  I was worried I was going to have to do a bunch of RE, but looks like you guys got it all figured out!  I am probably going to start getting involved with the PFS173 since I think it might be possible to run ColorChord on it.  Also, I may port some of your guys flashing code to the ESP8266 for drag-n-drop browser flashing.

Mostly just wanted to stop in and say this is amazing work on everyone's part. I can't wait for Padauk to take the uC world by storm since it looks like Microchip has been less and less proactive. (I was expecting the ATTiny202's etc... to come in smaller packages.  SOICs are just TOO BIG.)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cnlohr on May 08, 2019, 12:38:42 am
First of all AMAZING WORK EVERYONE WOW

1) I cannot use GPL-code in this application if I do a port to the '8266, since portions of it will need to be open and other portions not, so I am going to need to re-work things :(.  Would you guys consider using MIT/X11 or NewBSD licenses?
2) Any idea how sensitive the voltages are, for instance what the optimal values are for VPP and VDD at different stages?  Do we ever /need/ to set VPP higher than 8.3V?
3) Why didn't you guys go STM32F042 I didn't see anyone mentioning it?  The crystal-less operation makes things really convenient and cheap.  Also, I have a hid mode ser up for it if you were interested, so you wouldn't need any special udev rules and Windows operation would be trivial :). I'm still shooting for an ESP8266 version, but, would you be interested in a stm32f042 port if I feel the urge?
4) Is there a re-host for the fpdk_ic_table stuff.
5) Going forward, is sdcc-pdk going to continue to be maintained within github directly?  I'm honestly having a hard time getting it to work in emscripten but I'll keep poking at it.
6) I would be interested in directly contributing to the free-pdk group and just cleaning things up documentation wise as I see it.

I'm still shooting for ColorChord on my PFS173, but, the no-multiply-unit thing is really killing me.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 08, 2019, 07:35:57 am
do a port to the '8266
I wonder what the usecase for that is? For example for me it would be much more work to integrate the esp into my network than just to plug in a usb cable.

2) Any idea how sensitive the voltages are, for instance what the optimal values are for VPP and VDD at different stages?  Do we ever /need/ to set VPP higher than 8.3V?
VPP must go to 10.8. There are some reports of problems when not getting the voltages right in this thread.

3) Why didn't you guys go STM32F042 I didn't see anyone mentioning it?  The crystal-less operation makes things really convenient and cheap.
The ´72 is very similar, also does crystal-less. But the ´42 is not as common and more expensive.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cnlohr on May 08, 2019, 05:16:56 pm
do a port to the '8266
I wonder what the usecase for that is? For example for me it would be much more work to integrate the esp into my network than just to plug in a usb cable.
A side-goal of mine is I want to make an arduino-style development environment, that is 100% web-based. This part is purely for funzies.  It's something I've wanted to dink with for a while.  Currently most of the web-based ones are for high-level languages, but these are not interesting to me, and this here affords me an opportunity to cut my teeth with web-based compilation.  EDIT: Because of the power rail complexity, I am definitely feeling discouraged from an ESP8266 solution.

2) Any idea how sensitive the voltages are, for instance what the optimal values are for VPP and VDD at different stages?  Do we ever /need/ to set VPP higher than 8.3V?
VPP must go to 10.8. There are some reports of problems when not getting the voltages right in this thread.
Understood.

3) Why didn't you guys go STM32F042 I didn't see anyone mentioning it?  The crystal-less operation makes things really convenient and cheap.
The ´72 is very similar, also does crystal-less. But the ´42 is not as common and more expensive.

The '72 is much more expensive than the '42.  A while go, the cost difference for the crystal + a '70 was sufficient to warrant the '42, but now the cost difference looks like it's pulled ahead to almost $0.10... $0.05 for the added through-hole assy cost + $0.05 for a crystal.  Looks like it's about a wash now.  Just something to keep in mind in the future.


NEW Q:
Are there any other hangouts or areas that people interested in the Padauk chips hang out in?  I've read all the way through this thread, and want to make sure I don't make redundant work for folks.

EDIT:
There were other design decisions that I really questioned, but as I've read more and looked into it more, I'm starting to understand the rationale behind them.  This is a really awesome design both from a software and hardware end!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 09, 2019, 11:40:32 am
Hi,

STM32F072 is by far the most cheap processor fulfilling the requirements I had in mind:

- USB for easy power supply and connectivity
- 2x DAC to create different VPP and VDD voltage references (no DAC on STM32F042)
- 2x ADC to read/monitor the final (amplified) VPP/VDD
- enough IO for all data lines
- > 12kB of RAM to hold the max. complete program (3k words @ 16 bit) (STM32F042 has only 6 kB!)
- good price (STM32F072C8T6 $1.1 compared to STM32F042C6T6 $1.4 ==> source: lcsc.com) (the cheaper F042 variants do not have enough IO)

The crystal I added is for calibration of the written IC. Crystalless operation would require to have USB connected to sync to the SOF in order to have a relatively good clock for reference, but still drifting. This would make a standalone use of the programmer (just with a battery pack) impossible.
But it is possible just to not solder the crystal and use it since the STM32F072 has also crystalless mode.


Comment for choice of serial port:
* Windows 10 auto downloads the correct driver, works out of the box (only on older Windows you just need to install the "signed" driver form ST which is included in the release)
* macOS does not need any driver, works out of the box
* Linux does not need any driver, works out of the box (udev rule is only for "speed up" of the availability of the programmer after attaching USB. Some older Linux distributions bundled "Modem Manager" which always spends some seconds with every new attached serial port to find out if it is a telephony modem...)

Any HID implementation need to take into account that:
* HID is specified to be unreliable (you need to handle packet loss/drop yourself which makes the protocol more complex)
* HID with Linux is also not easy. Either you need ROOT permissions for running your software or you need ROOT permissions to install libusb in order to access HID for normal user programs.


Comments ESP8266:
* not sure if ESP8266 has 5V tolerant pins which you really need to have
* any non USB solution (e.g. with ESP8266) would need an extra power supply

Regarding GPL: The GPL was chosen intentionally for a good reason. Only fully open source should be the goal of the open source programmer we try to create here. There are no plans to re-license anything.


JS

BTW:
In development branch of the programmer software ( https://github.com/free-pdk/easy-pdk-programmer-software/tree/development ) you can see that I added several new IC types (probe/read for now).
I already identified 2 more protocol variants. It looks like the older processor generations require *all* 8 pins ( 3: VDD/VPP/GND + 5: CLK,DATIN,DATOUT,CLK2,ACK) for programming.
Out of pure luck the existing design of the programmer can be used for all of them :)

Yesterday I got my order from LCSC.com. I think I have all PADAUK and PUOLOP ICs now which I can easily source from public sellers:

UPDATE: The PUOLOP ICs are 100% identical compared to their PADAUK pendants. Exact same IC ID is reported when probing/reading. -> There are no Puolop specific ICs.

Work in progress in development branch (most are probe/read only right now):

./easypdkprog list
Supported ICs:
 PMC251   (0x058): OTP  : 1024 (16 bit), RAM:  96 bytes
 PMS132   (0x109): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS132B  (0x109): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes
 PMS152   (0xA27): OTP  : 1280 (14 bit), RAM:  80 bytes
 PMS271   (0xA58): OTP  : 1024 (16 bit), RAM:  64 bytes
 PFS154   (0xAA1): FLASH: 2048 (14 bit), RAM: 128 bytes
 PMS133   (0xC19): OTP  : 4096 (15 bit), RAM: 256 bytes
 PMS134   (0xC19): OTP  : 4096 (15 bit), RAM: 256 bytes
 PMS131   (0xC83): OTP  : 1536 (14 bit), RAM:  88 bytes
 PMS171B  (0xD36): OTP  : 1536 (14 bit), RAM:  96 bytes
 PMS154B  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS154C  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PFS173   (0xEA2): FLASH: 3072 (15 bit), RAM: 256 bytes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 10, 2019, 05:00:24 pm
How about the Puolop PTBO164SX? According to Puolop, it has 1.75 KW of ROM, but I don't see a part with that amount of ROM in the Padauk catalog.

According to my understanding and communication with Padauk, Puolop is a reseller of Padauk devices. However, Padauk also makes customer-specific devices. Could it be that the PTBO164SX is a device made by Padauk exclusively for Puolop?

Philipp

P.S.: There are actually a few places in the pdf metadata of the Puolop datasheet, where a PMC164 is mentioned. I guess we can assume that Padauk made the device using PMC164 as the internal name for Puolop, who uses the name PTBO164SX (and just replaced the text in the datasheet given to them by Padauk forgetting a few places).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 10, 2019, 11:28:08 pm
How about the Puolop PTBO164SX? According to Puolop, it has 1.75 KW of ROM, but I don't see a part with that amount of ROM in the Padauk catalog.

Unfortunately I could not find any place where this IC is sold.

@contributors from SZ: Puolop HQ is in SZ. Maybe someone can talk to them or go there and get some of the mysterious PTBO164 ?

JS

EDIT: Not so mysterious after all. PADAUK IDE has a "PMS164.INC" include file. OTP-ID is 0x2A31. RAM-SIZE is 0x80 and ROM-SIZE is 0x800 (same as PMS/PFS154).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 29, 2019, 02:14:19 pm
The adapter pcbs for Padauk controllers in SOT23-6 I designed arrived recently. I could test them successfully with a PMS150C-U06. Unfortunately I couldn't persuade LCSC yet to add PFS154-U06 to their catalog.

You can download all source files and documentation from here:
https://github.com/electroniceel/easy-pdk-programmer-hardware/tree/adapter-pcbs/adapter-pcbs (https://github.com/electroniceel/easy-pdk-programmer-hardware/tree/adapter-pcbs/adapter-pcbs)
Update: the adapter files have been merged and you can now get them from here:
https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs (https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs)

I also uploaded a set of gerbers of a complete panel with the programmer and all my adapters. When I ordered this at JLCPCB I didn't have to pay any extra fee for the panel. But I heard that they recently changed their policy and now charge extra for a panel with different pcbs on it. So YMMV or maybe try another pcb service like Elecrow.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 31, 2019, 06:27:25 pm
@js: thanks for merging my stuff.

I have a question about the clock calibration: when you presented the calibration logic in https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2184683/#msg2184683 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2184683/#msg2184683), you used #defines like EASY_PDK_CALIBRATE_IHRC.

Is there a header file with these defines available somewhere? If not, wouldn't it make sense to publish it and provide it in the easy-pdk-programmer-software package or with sdcc?

@spth: do you think it is possible and makes sense to publish such a header with sdcc? I think it would make the code more portable since the header directory of sdcc itself is usually automatically searched for header files, while the correct header directory of easy-pdk-programmer-software would have to be located first by some kind of script, autotools, cmake,...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 01, 2019, 04:14:03 pm
Hi,

I'm working on header file(s). I started to create them while doing some real projects.

Right now I'm undecided if we should have multiple includes, different for each variant, or a generic one with sections specific to architectures like 13/14/15/16 bit.

Attached is my current WORK IN PROGRESS version (one big include file for all). It includes the calibration definitions and many other useful stuff.

JS

Here some examples where I use it:

typical sdcc_external_startup implementation:
Code: [Select]
unsigned char _sdcc_external_startup(void)
{
  PDK_INIT_SYSCLOCK_4MHZ();                   //use 4MHz so we can use 3.0V VDD
  EASY_PDK_CALIBRATE_IHRC(4000000,3000);      //tune SYSCLK = 4MHz @ 3.000V
  return 0;                                   //perform normal initialization
}

interrupt:
Code: [Select]
void interrupt(void) __interrupt(0)
{
  if(_intrq & INTRQ_T16)                      //interrupt request for timer16?
  {
    //do something here...

    _intrq &= ~INTRQ_T16;                     //clear this interrupt request
  }
}

SPI send receive in assembler (universal version, works with 13bit):
Code: [Select]
#define SPI_PORT        _pa
#define SPI_PORTC       _pac
#define SPI_NCS_PIN     4
#define SPI_CLK_PIN     0
#define SPI_OUT_PIN     6
#define SPI_IN_PIN      7

//...

uint8_t SPI_SendReceive(uint8_t s)
{
  __asm__(
    "  mov a, #8                                      \n"  //loop 8 times
    "__SPI_SNDRCV_BIT:                                \n"
    "  set0 "_ASMV(SPI_PORT)", #"_ASMD(SPI_OUT_PIN)"  \n"  //SPI-OUT = 0
    "  t0sn _SPI_SendReceive_PARM_1, #7               \n"  //s.7==0 ?
    "  set1 "_ASMV(SPI_PORT)", #"_ASMD(SPI_OUT_PIN)"  \n"  //SPI-OUT = 1
    "  set1 "_ASMV(SPI_PORT)", #"_ASMD(SPI_CLK_PIN)"  \n"  //SPI-CLK = 1
    "  sl _SPI_SendReceive_PARM_1                     \n"  //s<<=1
    "  t0sn "_ASMV(SPI_PORT)", #"_ASMD(SPI_IN_PIN)"   \n"  //SPI-IN==0 ?
    "  set1 _SPI_SendReceive_PARM_1, #0               \n"  //s.0=1
    "  set0 "_ASMV(SPI_PORT)", #"_ASMD(SPI_CLK_PIN)"  \n"  //SPI-CLK = 0
    "  dzsn a                                         \n"  //loop--
    "  goto __SPI_SNDRCV_BIT                          \n"  //loop again if>0
  );
  return s;
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on June 02, 2019, 10:47:38 am
Attached is my current WORK IN PROGRESS version (one big include file for all). It includes the calibration definitions and many other useful stuff.
thanks for posting. This is indeed much more than just the cal definitions.

I think it would make sense to split it up into different files according to pdk-architecture or controllers, maybe also by functions, like cal definition, register definition and so on. But I suggest you first put it up on github so that others can better contribute. Then we can try out what kind of structuring makes most sense, maybe evolve it over time.

Also I still think it may be an option to include it into sdcc. That would make using it easier. But contributing changes would become more complicated as all changes would have to go through the sdcc svn and can't just be merged in github.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: GromBeestje on June 23, 2019, 03:39:46 pm
Regarding GPL: I see the firmware uses ST's USB middleware, which is under ST's SLA0044 license. Ain't this incompatible with GPL (eg. Do you need a linking exception to allow the ST USB Middleware to be used?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 25, 2019, 10:09:26 am
Hi,

The developed FREE-PDK software is GPL. This is the authors choice and 100% valid.

Regarding ST USB middleware and SLA0044. Not sure which paragraph of SLA0044 you see as problematic.

I see the firmware uses ST's USB middleware, which is under ST's SLA0044 license.
->(1) The USB middleware source code by itself is still under ST license (see file headers of ST USB middleware for details).

Ain't this incompatible with GPL (eg. Do you need a linking exception to allow the ST USB middleware to be used?
->(2) It is explicitly allowed to use the compiled firmware containing ST code to be used on ST microprocessors (which is the case here).

Even the explicit mentioned GPL in (5) refers to another fact. It tries to make clear that the middleware software from ST can never become GPL licensed (which is not the case here, it still falls under the original ST license visible in all ST files).

Maybe this will not fulfill the strict 100% GPL requirements of a complete compiled software package required from some Linux distributions like Debian and therefor the software can not be bundled with Debian but this does not mean that there is a problem using GPL for the FREE-PDK software.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on June 26, 2019, 08:02:05 am
The developed FREE-PDK software is GPL. This is the authors choice and 100% valid.
I don't think GromBeestje questioned this.

Even the explicit mentioned GPL in (5) refers to another fact. It tries to make clear that the middleware software from ST can never become GPL licensed (which is not the case here, it still falls under the original ST license visible in all ST files).
The problem is that this is incompatible with the GPL. The GPL requires that all parts of the program are compatible with the GPL. As the ST files are linked into the final program, you can't distribute a binary that complies with the GPL.

Maybe this will not fulfill the strict 100% GPL requirements of a complete compiled software package required from some Linux distributions like Debian and therefor the software can not be bundled with Debian but this does not mean that there is a problem using GPL for the FREE-PDK software.
It means noone, not just linux distributions, is allowed to distribute binary packages of free-pdk as it can't be done in a legally clean manner that complies with the GPL and the SLA0044. i idea. The moment there are contributions from other people in the codebase, even you can't distribute compiled binaries on github anymore unless you have the written permission of all contributors to publish these binaries under a different license than the GPL (as the GPL forbids distributing stuff linked with GPL-incompatible parts). I don't think this is what you intended.

The solution GromBeestje suggested is a good alternative I think: The code stays GPL, but with an added exception that the code may be linked with the ST usb middleware. Then everyone is allowed to distribute binaries, but it does not allow anyone to modify free-pdk without providing the source under gpl conditions.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 27, 2019, 01:32:46 pm
Hmmmm,

I never looked at it like this.

To me it looks a bit strange to add a text like this:

"GPL linking exception for FREE PDK Programmer STM32 firmware binary: You are allowed to compile and link the complete code from this repository, including the included ST USB middleware, in order to build a binary firmware which you can use on the STM32 based Free PDK programmer."

Do you think this will solve the "problem"?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on June 27, 2019, 03:46:27 pm
"GPL linking exception for FREE PDK Programmer STM32 firmware binary: You are allowed to compile and link the complete code from this repository, including the included ST USB middleware, in order to build a binary firmware which you can use on the STM32 based Free PDK programmer."
The GPL doesn't forbid you to compile and link something non-GPL-compliant, it forbids you to distribute this binary. Unfortunately careful wording is required to avoid the pitfalls of legalese...

GPL exceptions are a common thing and I suggest to re-use and adapt what others have done. It looks like for example wget uses something that would fit. See https://en.wikipedia.org/wiki/Wget#License (https://en.wikipedia.org/wiki/Wget#License).

I suggest to adapt it like this:

Code: [Select]
Additional permission under GNU GPL version 3 section 7

If you modify this program, or any covered work, by linking or combining it with the STMicroelectronics STM32 USB Device Library (or a modified version of that library),
you are granted additional permission to convey the resulting work. Corresponding Source for a non-source form of such a combination shall include the source code for the
parts of the STM32 USB Device Library used as well as that of the covered work.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 28, 2019, 10:04:33 am
"GPL linking exception for FREE PDK Programmer STM32 firmware binary: You are allowed to compile and link the complete code from this repository, including the included ST USB middleware, in order to build a binary firmware which you can use on the STM32 based Free PDK programmer."
The GPL doesn't forbid you to compile and link something non-GPL-compliant, it forbids you to distribute this binary. Unfortunately careful wording is required to avoid the pitfalls of legalese...

GPL exceptions are a common thing and I suggest to re-use and adapt what others have done. It looks like for example wget uses something that would fit. See https://en.wikipedia.org/wiki/Wget#License (https://en.wikipedia.org/wiki/Wget#License).

I suggest to adapt it like this:

Code: [Select]
Additional permission under GNU GPL version 3 section 7

If you modify this program, or any covered work, by linking or combining it with the STMicroelectronics STM32 USB Device Library (or a modified version of that library),
you are granted additional permission to convey the resulting work. Corresponding Source for a non-source form of such a combination shall include the source code for the
parts of the STM32 USB Device Library used as well as that of the covered work.

Hi electronic_eel,

Thank you very much for digging this out and your suggestion. I will adapt this and extend the license of the firmware code using the text from you.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 30, 2019, 11:52:38 am
Hi,

To understand the register mappings on different PDK CPU types better I created a list (based on include files from original IDE).

https://github.com/free-pdk/fppa-pdk-documentation/blob/master/PDK_register_mapping_scroll_right.csv

Attached is a colorful version as PNG from it.

Based on this info (most registers jump around for different types and only a few number remains static) I think the best idea would be to create one include file per supported processor like:

pdk/pmc150c.h
pdk/pfs154.h
pdk/pfs173.h
...

Comments? Suggestions?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 01, 2019, 05:45:50 am
Quote
Hi,

To understand the register mappings on different PDK CPU types better I created a list (based on include files from original IDE).

https://github.com/free-pdk/fppa-pdk-documentation/blob/master/PDK_register_mapping_scroll_right.csv

Attached is a colorful version as PNG from it.

Based on this info (most registers jump around for different types and only a few number remains static) I think the best idea would be to create one include file per supported processor like:

pdk/pmc150c.h
pdk/pfs154.h
pdk/pfs173.h
...

Comments? Suggestions?


JS
I agree with you, also we can copy what ST has done to STM32, and the HAL and libraries for them, they are very good :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vollmars on July 01, 2019, 12:11:04 pm
Hi,

To understand the register mappings on different PDK CPU types better I created a list (based on include files from original IDE).

https://github.com/free-pdk/fppa-pdk-documentation/blob/master/PDK_register_mapping_scroll_right.csv

Attached is a colorful version as PNG from it.

Based on this info (most registers jump around for different types and only a few number remains static) I think the best idea would be to create one include file per supported processor like:

pdk/pmc150c.h
pdk/pfs154.h
pdk/pfs173.h
...

Comments? Suggestions?


JS

Hi,

thank you, for all the work you done.
In the table i miss the Timer3 registers for the PFS154.

vollmars
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 02, 2019, 08:48:32 pm
In the table i miss the Timer3 registers for the PFS154.

Yes I forgot TM3 for PFS154, but for sure there are more mistakes in the table. I just did it to get an idea of the register mapping.

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: lanserge on July 23, 2019, 06:37:38 pm
Hi, Guys

I have joined the forum to say big thank you for the work you have done.

Today I managed to get stable read and write PMS150c-u06 with the knowledge from this forum.
I made programmer from mostly assembled modules from e-bay.
I used ready MT3608 step up module to get 16V out of 5V.
I used two MCP4725 modules to have two programmable DACs (on one of the modules I soldered jumper to have different address on I2C).
Also I soldered LM358S-13 IC  on DIP adapter, double OP-AMP powered from 16V to get programmable VDD and VPP: each op-amp has plus input connected to corresponded MCP4725 module output, minus input connected to voltage divider with 8.2k to the ground and 16.2k to the op-amp output.
Basically idea from here: http://henrysbench.capnfatz.com/henrys-bench/arduino-projects-tips-and-more/a-powerful-little-arduino-programmable-10v-supply/ (http://henrysbench.capnfatz.com/henrys-bench/arduino-projects-tips-and-more/a-powerful-little-arduino-programmable-10v-supply/)  but without transistor (small current expected).
And finally I used CH341A mini programmer with I2C connected to MCP4725 modules and other pins in next order:
D0 which is marked as CS on the board connected to chip MISO (the D7 MISO on CH341 is not suitable,
because needs to be D0-D5 for bit banging)
D3 which is marked as SCK - to chip SCK
D5 which is marked as MOSI - to chip MOSI
I set chip VDD and VPP via I2C programming MCP4725 modules and
I wrote my own python code that utilising bitbanging protocol of the CH341A IC to do the rest.
The target VDD used is 5V.
So everything works and I checked everything with my Saleae logic analyser.

The only question I have is some odd behaviour I found.
If I use aborted write cycle to read chip ID I get 0xA16 but if I use second read cycle I always get 0x50B which is obviously shifted by a bit to the right.
So my question is which is actually right ID? Who said it should be 0xA16 and not 0x50B?
Also if I have aborted write cycle I need to power off IC because the state machine is off but with read cycle everything continue to work stable.
So I prefer the second way.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on July 24, 2019, 04:25:33 am
I haven't followed this thread for a long time, but it sounds like there has been huge progress in this?
Can someone give me a TLDR; of the current status?
Thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on July 24, 2019, 06:26:29 am
The programming algorithm for many Padauk microcontrollers is reverse engineered, a C compiler (SDCC) was ported to it and is stable for most types, an open source programmer was developed and many chips could be flashed successfully.

Details:
- my 4 channel ADC project, with which I sampled the programming signals of an original Padauk programmer:  https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2075176/ (https://www.eevblog.com/forum/projects/4-channel-adc-10-mhz-8-bit-design/msg2075176/)
- sample recording: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2096917/#msg2096917)
- first protocol reverse engineering: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2099854/#msg2099854 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2099854/#msg2099854)
- open source hardware programmer: https://github.com/free-pdk/easy-pdk-programmer-hardware (https://github.com/free-pdk/easy-pdk-programmer-hardware)
- C compiler: https://github.com/free-pdk/sdcc-pdk-code-examples (https://github.com/free-pdk/sdcc-pdk-code-examples)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 24, 2019, 07:39:25 am
Quote
C compiler: https://github.com/free-pdk/sdcc-pdk-code-examples
Thanks for the info, this link is only the examples, though I installed SDCC, how to compile the examples? what's the command?
There is no makefile with the examples and compiling the count-pfs154 example with this command generate lot's of errors and warnings!


(https://img.techpowerup.org/190724/untitled681.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on July 24, 2019, 09:48:48 am
I downloaded the latest snapshot of SDCC from this site (http://sdcc.sourceforge.net/snap.php) (was sdcc-snapshot-amd64-unknown-linux2.5-20190723-11326.tar.bz2 for my Linux system). Then I could compile it like this:
Code: [Select]
~/sdcc/bin/sdcc -lpdk15 -mpdk15 count.c

It creates a lot of output files:

Code: [Select]
-rw-r--r-- 1 frank frank  4424 Jul 24 11:44 count.sym
-rw-r--r-- 1 frank frank 19123 Jul 24 11:44 count.rst
-rw-r--r-- 1 frank frank  6046 Jul 24 11:44 count.rel
-rw-r--r-- 1 frank frank  8774 Jul 24 11:44 count.map
-rw-r--r-- 1 frank frank 19123 Jul 24 11:44 count.lst
-rw-r--r-- 1 frank frank   192 Jul 24 11:44 count.lk
-rw-r--r-- 1 frank frank  1132 Jul 24 11:44 count.ihx
-rw-r--r-- 1 frank frank     0 Jul 24 11:44 count.cdb
-rw-r--r-- 1 frank frank  1720 Jul 24 11:37 count.c
-rw-r--r-- 1 frank frank  6843 Jul 24 11:44 count.asm

I think the ihx file then can be programmed with easypdkprog, as you can see here (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2311989/#msg2311989).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 24, 2019, 01:02:28 pm
Thanks FrankBuss :-+ :-+ :-+
That works here too, how did you find the commands -lpdk15 -mpdk15, there is nothing like them in the help

If I just type SDCC in the command
Quote
SDCC : mcs51/z80/z180/r2k/r3ka/gbz80/tlcs90/ez80_z80/ds390/pic16/pic14/TININative/ds400/hc08/s08/stm8/pdk14/pdk15 3.9.0 #11195 (MINGW64)
published under GNU General Public License (GPL)
Usage : sdcc [options] filename
Options :-

General options:
      --help                Display this help
  -v  --version             Display sdcc's version
      --verbose             Trace calls to the preprocessor, assembler, and linker
  -V                        Execute verbosely. Show sub commands as they are run
  -d                        Output list of mcaro definitions in effect. Use with -E
  -D                        Define macro as in -Dmacro
  -I                        Add to the include (*.h) path, as in -Ipath
  -A
  -U                        Undefine macro as in -Umacro
  -M                        Preprocessor option
  -W                        Pass through options to the pre-processor (p), assembler (a) or linker (l)
  -S                        Compile only; do not assemble or link
  -c  --compile-only        Compile and assemble, but do not link
  -E  --preprocessonly      Preprocess only, do not compile
      --c1mode              Act in c1 mode.  The standard input is preprocessed code, the output is assembly code.
  -o                        Place the output into the given path resp. file
      --print-search-dirs   display the directories in the compiler's search path
      --vc                  messages are compatible with Micro$oft visual studio
      --use-stdout          send errors to stdout instead of stderr
      --nostdlib            Do not include the standard library directory in the search path
      --nostdinc            Do not include the standard include directory in the search path
      --less-pedantic       Disable some of the more pedantic warnings
      --disable-warning     <nnnn> Disable specific warning
      --Werror              Treat the warnings as errors
      --debug               Enable debugging symbol output
      --cyclomatic          Display complexity of compiled functions
      --std-c89             Use ISO C90 (aka ANSI C89) standard (slightly incomplete)
      --std-sdcc89          Use ISO C90 (aka ANSI C89) standard with SDCC extensions
      --std-c95             Use ISO C95 (aka ISO C94) standard (slightly incomplete)
      --std-c99             Use ISO C99 standard (incomplete)
      --std-sdcc99          Use ISO C99 standard with SDCC extensions
      --std-c11             Use ISO C11 standard (incomplete)
      --std-sdcc11          Use ISO C11 standard with SDCC extensions (default)
      --std-c2x             Use ISO C2X standard (incomplete)
      --std-sdcc2x          Use ISO C2X standard with SDCC extensions
      --fdollars-in-identifiers  Permit '$' as an identifier character
      --fsigned-char        Make "char" signed by default
      --use-non-free        Search / include non-free licensed libraries and header files

Code generation options:
  -m                        Set the port to use e.g. -mz80.
  -p                        Select port specific processor e.g. -mpic14 -p16f84
      --stack-auto          Stack automatic variables
      --xstack              Use external stack
      --int-long-reent      Use reentrant calls on the int and long support functions
      --float-reent         Use reentrant calls on the float support functions
      --xram-movc           Use movc instead of movx to read xram (xdata)
      --callee-saves        <func[,func,...]> Cause the called function to save registers instead of the caller
      --profile             On supported ports, generate extra profiling information
      --fomit-frame-pointer  Leave out the frame pointer.
      --all-callee-saves    callee will always save registers used
      --stack-probe         insert call to function __stack_probe at each function prologue
      --no-xinit-opt        don't memcpy initialized xram from code
      --no-c-code-in-asm    don't include c-code as comments in the asm file
      --no-peep-comments    don't include peephole optimizer comments
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment

Optimization options:
      --nooverlay           Disable overlaying leaf function auto variables
      --nogcse              Disable the GCSE optimisation
      --nolabelopt          Disable label optimisation
      --noinvariant         Disable optimisation of invariants
      --noinduction         Disable loop variable induction
      --noloopreverse       Disable the loop reverse optimisation
      --no-peep             Disable the peephole assembly file optimisation
      --no-reg-params       On some ports, disable passing some parameters in registers
      --peep-asm            Enable peephole optimization on inline assembly
      --peep-return         Enable peephole optimization for return instructions
      --no-peep-return      Disable peephole optimization for return instructions
      --peep-file           <file> use this extra peephole file
      --opt-code-speed      Optimize for code speed rather than size
      --opt-code-size       Optimize for code size rather than speed
      --max-allocs-per-node  Maximum number of register assignments considered at each node of the tree decomposition
      --nolospre            Disable lospre
      --allow-unsafe-read   Allow optimizations to read any memory location anytime
      --nostdlibcall        Disable optimization of calls to standard library

Internal debugging options:
      --dump-ast            Dump front-end AST before generating i-code
      --dump-i-code         Dump the i-code structure at all stages
      --dump-graphs         Dump graphs (control-flow, conflict, etc)
      --i-code-in-asm       Include i-code as comments in the asm file
      --fverbose-asm        Include code generator comments in the asm output

Linker options:
  -l                        Include the given library in the link
  -L                        Add the next field to the library search path
      --lib-path            <path> use this path to search for libraries
      --out-fmt-ihx         Output in Intel hex format
      --out-fmt-s19         Output in S19 hex format
      --xram-loc            <nnnn> External Ram start location
      --xram-size           <nnnn> External Ram size
      --iram-size           <nnnn> Internal Ram size
      --xstack-loc          <nnnn> External Stack start location
      --code-loc            <nnnn> Code Segment Location
      --code-size           <nnnn> Code Segment size
      --stack-loc           <nnnn> Stack pointer initial value
      --data-loc            <nnnn> Direct data start location
      --idata-loc
      --no-optsdcc-in-asm   Do not emit .optsdcc in asm

Special options for the mcs51 port:
      --model-small         internal data space is used (default)
      --model-medium        external paged data space is used
      --model-large         external data space is used
      --model-huge          functions are banked, data in external space
      --stack-size          Tells the linker to allocate this space for stack
      --parms-in-bank1      use Bank1 for parameter passing
      --pack-iram           Tells the linker to pack variables in internal ram (default)
      --no-pack-iram        Deprecated: Tells the linker not to pack variables in internal ram
      --acall-ajmp          Use acall/ajmp instead of lcall/ljmp
      --no-ret-without-call  Do not use ret independent of acall/lcall

Special options for the z80 port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the z180 port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the r2k port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the r3ka port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the gbz80 port:
      -bo                   <num> use code bank <num>
      -ba                   <num> use data bank <num>
      --callee-saves-bc     Force a called function to always save BC
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel

Special options for the tlcs90 port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the ez80_z80 port:
      --callee-saves-bc     Force a called function to always save BC
      --portmode=           Determine PORT I/O mode (z80/z180)
      --asm=                Define assembler name (rgbds/asxxxx/isas/z80asm)
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --dataseg             <name> use this name for the data segment
      --no-std-crt0         For the z80/gbz80 do not link default crt0.rel
      --reserve-regs-iy     Do not use IY (incompatible with --fomit-frame-pointer)
      --oldralloc           Use old register allocator
      --fno-omit-frame-pointer  Do not omit frame pointer
      --emit-externs        Emit externs list in generated asm

Special options for the ds390 port:
      --model-flat24        use the flat24 model for the ds390 (default)
      --stack-8bit          use the 8bit stack for the ds390 (not supported yet)
      --stack-size          Tells the linker to allocate this space for stack
      --pack-iram           Tells the linker to pack variables in internal ram (default)
      --no-pack-iram        Deprecated: Tells the linker not to pack variables in internal ram
      --stack-10bit         use the 10bit stack for ds390 (default)
      --use-accelerator     generate code for ds390 arithmetic accelerator
      --protect-sp-update   will disable interrupts during ESP:SP updates
      --parms-in-bank1      use Bank1 for parameter passing

Special options for the pic16 port:
      --pstack-model=       use stack model 'small' (default) or 'large'
  -y  --extended            enable Extended Instruction Set/Literal Offset Addressing mode
      --pno-banksel         do not generate BANKSEL assembler directives
      --obanksel=           set banksel optimization level (default=0 no)
      --denable-peeps       explicit enable of peepholes
      --no-optimize-goto    do NOT use (conditional) BRA instead of GOTO
      --optimize-cmp        try to optimize some compares
      --optimize-df         thoroughly analyze data flow (memory and time intensive!)
      --asm=                Use alternative assembler
      --mplab-comp          enable compatibility mode for MPLAB utilities (MPASM/MPLINK)
      --link=               Use alternative linker
      --preplace-udata-with=  Place udata variables at another section: udata_acs, udata_ovr, udata_shr
      --ivt-loc=            Set address of interrupt vector table.
      --nodefaultlibs       do not link default libraries when linking
      --use-crt=            use <crt-o> run-time initialization module
      --no-crt              do not link any default run-time initialization module
      --debug-xtra          show more debug info in assembly output
      --debug-ralloc        dump register allocator debug file *.d
      --pcode-verbose       dump pcode related info
      --calltree            dump call tree in .calltree file
      --gstack              trace stack pointer push/pop to overflow
      --no-warn-non-free    suppress warning on absent --use-non-free option

Special options for the pic14 port:
      --debug-xtra          show more debug info in assembly output
      --no-pcode-opt        disable (slightly faulty) optimization on pCode
      --stack-size          sets the size if the argument passing stack (default: 16, minimum: 4)
      --no-extended-instructions  forbid use of the extended instruction set (e.g., ADDFSR)
      --no-warn-non-free    suppress warning on absent --use-non-free option

Special options for the TININative port:
      --model-flat24        use the flat24 model for the ds390 (default)
      --stack-8bit          use the 8bit stack for the ds390 (not supported yet)
      --stack-size          Tells the linker to allocate this space for stack
      --pack-iram           Tells the linker to pack variables in internal ram (default)
      --no-pack-iram        Deprecated: Tells the linker not to pack variables in internal ram
      --stack-10bit         use the 10bit stack for ds390 (default)
      --use-accelerator     generate code for ds390 arithmetic accelerator
      --protect-sp-update   will disable interrupts during ESP:SP updates
      --parms-in-bank1      use Bank1 for parameter passing
      --tini-libid          <nnnn> LibraryID used in -mTININative

Special options for the ds400 port:
      --model-flat24        use the flat24 model for the ds400 (default)
      --stack-8bit          use the 8bit stack for the ds400 (not supported yet)
      --stack-size          Tells the linker to allocate this space for stack
      --pack-iram           Tells the linker to pack variables in internal ram (default)
      --no-pack-iram        Deprecated: Tells the linker not to pack variables in internal ram
      --stack-10bit         use the 10bit stack for ds400 (default)
      --use-accelerator     generate code for ds400 arithmetic accelerator
      --protect-sp-update   will disable interrupts during ESP:SP updates
      --parms-in-bank1      use Bank1 for parameter passing

Special options for the hc08 port:
      --model-small         8-bit address space for data
      --model-large         16-bit address space for data (default)
      --out-fmt-elf         Output executable in ELF format
      --oldralloc           Use old register allocator

Special options for the s08 port:
      --model-small         8-bit address space for data
      --model-large         16-bit address space for data (default)
      --out-fmt-elf         Output executable in ELF format
      --oldralloc           Use old register allocator

Special options for the stm8 port:
      --model-medium        16-bit address space for both data and code (default)
      --model-large         16-bit address space for data, 24-bit for code
      --codeseg             <name> use this name for the code segment
      --constseg            <name> use this name for the const segment
      --out-fmt-elf         Output executable in ELF format


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on July 24, 2019, 01:14:42 pm
Page 28 of the manual.

http://sdcc.sourceforge.net/doc/sdccman.pdf (http://sdcc.sourceforge.net/doc/sdccman.pdf)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 25, 2019, 09:17:10 am
Quote
open source hardware programmer: https://github.com/free-pdk/easy-pdk-programmer-hardware

I have checked it, it has only the hardware files, where is the software files for the STM32 MCU and also the PC side software
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: FrankBuss on July 25, 2019, 11:11:22 am
Quote
open source hardware programmer: https://github.com/free-pdk/easy-pdk-programmer-hardware

I have checked it, it has only the hardware files, where is the software files for the STM32 MCU and also the PC side software
There is a message at the bottom of the page: "Software sources can be found here" and then a link.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 25, 2019, 12:19:56 pm
The only question I have is some odd behaviour I found.
If I use aborted write cycle to read chip ID I get 0xA16 but if I use second read cycle I always get 0x50B which is obviously shifted by a bit to the right.
So my question is which is actually right ID? Who said it should be 0xA16 and not 0x50B?

Hi,

just have a look in the PADAUK IDE header file: "PMS150C.INC":
...
.Assembly   OTP_ID      2A16h
...
Usually this matches the processor ID response (with some exceptions). Only the lower 12 bits are honored for all processors: => 0xA16  :)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 25, 2019, 07:33:42 pm
Quote
There is a message at the bottom of the page: "Software sources can be found here" and then a link.
Thanks FrankBuss :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gaganchd2000 on July 28, 2019, 04:52:31 am
Hi

Probably this is very lame question here but still I need some help from experts. I have written blinky program in FPPA IDE and now want to burn code. But problem is I dont see .PDK file. I see only .c, .pre, .prj files.
Can you please let me know what i am missing.
I have chips and writer. No ICE.
 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 28, 2019, 08:38:53 am
Hi

Probably this is very lame question here but still I need some help from experts. I have written blinky program in FPPA IDE and now want to burn code. But problem is I dont see .PDK file. I see only .c, .pre, .prj files.
Can you please let me know what i am missing.
I have chips and writer. No ICE.

Hi,

A .PDK file is created in same folder as the project (.PRJ) file, which you choose to be at a different location than your source files: "C:\Users\gagan\Test_Blinky\Test_Blinky.PRJ".
So your .PDK file is here: "C:\Users\gagan\Test_Blinky\Test_Blinky.PDK"

If you just want to WRITE the compiled program to a chip, you don't have to leave the IDE.
There is a menu entry "Execute->Writer" which will open a writer dialog with all parameters filled in from your project.
The extra "WRITER.exe" is only for factories which mass produce ICs and do not need to open the compiler IDE.

BTW: Your IDE version (0.84) is a bit dated. There is a much newer (0.86) on PADAUK web site.

Last comment: Since this is the "Padauk Programmer Reverse Engineering" thread it would be nice if you consider using and improving the free open source tools (open hardware programmer / open source compiler) instead.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 29, 2019, 08:06:22 am
I have installed mingw on my windows machine and added the PATH to environment variables. also I have added make to my Git Bash!
How should I compile the PC software? I use this and I got  errors

Code: [Select]
make all

Quote
make all
cd lib/argp-standalone-1.3 && sh configure
checking for a BSD-compatible install... /usr/bin/install -c
checking whether build environment is sane... yes
checking for gawk... gawk
checking whether make sets $(MAKE)... yes
checking for gcc... gcc
checking for C compiler default output file name... a.exe
checking whether the C compiler works... yes
checking whether we are cross compiling... no
checking for suffix of executables... .exe
checking for suffix of object files... o
checking whether we are using the GNU C compiler... yes
checking whether gcc accepts -g... yes
checking for gcc option to accept ANSI C... none needed
checking for style of include used by make... GNU
checking dependency style of gcc... gcc3
checking whether make sets $(MAKE)... (cached) yes
checking for ranlib... ranlib
checking for gcc... (cached) gcc
checking whether we are using the GNU C compiler... (cached) yes
checking whether gcc accepts -g... (cached) yes
checking for gcc option to accept ANSI C... (cached) none needed
checking dependency style of gcc... (cached) gcc3
checking how to run the C preprocessor... gcc -E
checking for egrep... grep -E
checking for ANSI C header files... yes
checking for sys/types.h... yes
checking for sys/stat.h... yes
checking for stdlib.h... yes
checking for string.h... yes
checking for memory.h... yes
checking for strings.h... yes
checking for inttypes.h... yes
checking for stdint.h... yes
checking for unistd.h... yes
checking limits.h usability... yes
checking limits.h presence... yes
checking for limits.h... yes
checking malloc.h usability... yes
checking malloc.h presence... yes
checking for malloc.h... yes
checking for unistd.h... (cached) yes
checking for an ANSI C-conforming const... yes
checking for inline... inline
checking for size_t... yes
checking for __attribute__... no
checking for working alloca.h... yes
checking for alloca... yes
checking for vprintf... yes
checking for _doprnt... no
checking for strerror... yes
checking for mempcpy... no
checking for strndup... no
checking for strchrnul... no
checking for putc_unlocked('x', stdout)... no
checking for flockfile... no
checking for fputs_unlocked... no
checking for fwrite_unlocked... no
checking for strdup... yes
checking for asprintf... no
checking whether program_invocation_name is declared... no
checking whether program_invocation_short_name is declared... no
configure: creating ./config.status
config.status: creating Makefile
config.status: creating testsuite/Makefile
config.status: creating config.h
config.status: config.h is unchanged
config.status: executing depfiles commands
C:/Program Files/Git/mingw64/bin/make -C lib/argp-standalone-1.3
make[1]: Entering directory 'C:/Users/ASiDesigner/Desktop/easy-pdk-programmer-software-master/easy-pdk-programmer-software-master/lib/argp-standalone-1.3'
C:/Program Files/Git/mingw64/bin/make  all-recursive
make[2]: Entering directory 'C:/Users/ASiDesigner/Desktop/easy-pdk-programmer-software-master/easy-pdk-programmer-software-master/lib/argp-standalone-1.3'
Making all in .
/usr/bin/sh: line 11: C:/Program: No such file or directory
make[2]: *** [Makefile:325: all-recursive] Error 1
make[2]: Leaving directory 'C:/Users/ASiDesigner/Desktop/easy-pdk-programmer-software-master/easy-pdk-programmer-software-master/lib/argp-standalone-1.3'
make[1]: *** [Makefile:215: all] Error 2
make[1]: Leaving directory 'C:/Users/ASiDesigner/Desktop/easy-pdk-programmer-software-master/easy-pdk-programmer-software-master/lib/argp-standalone-1.3'
make: *** [Makefile:33: lib/argp-standalone-1.3/libargp.a] Error 2

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 30, 2019, 07:37:22 pm
I have installed mingw on my windows machine and added the PATH to environment variables. also I have added make to my Git Bash!
How should I compile the PC software? I use this and I got  errors

There are multiple options to get it working on Windows.

I added a compiled binary to the Github project RELEASES: https://github.com/free-pdk/easy-pdk-programmer-software/releases  (1.0 - easy-pdk-programmer-software-windows.zip)

If you want to compile it yourself the most easy way I know of is to install MSYS2 which can then be used directly or with the in MSYS2 integrated MINGW. The package manager pacman in MSYS2 makes installing required components and libraries very easy. You find a lot of information about this on the internet.

Your specific problem with your MinGW installation looks like you installed it to a path which includes spaces (I think this was/is a problem with MinGW, try "C:\MinGW" instead).
Your build stops when it is looking for a dependency tool and only half of the path is visible:


Code: [Select]
make all
...
make[2]: Entering directory 'C:/Users/ASiDesigner/Desktop/easy-pdk-programmer-software-master/easy-pdk-programmer-software-master/lib/argp-standalone-1.3'
Making all in .
/usr/bin/sh: line 11: C:/Program: No such file or directory
make[2]: *** [Makefile:325: all-recursive] Error 1
...

You can see that "C:/Program" seems to be the start of "C:/Program Files/..."


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 31, 2019, 05:54:59 am
Thanks JS :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 12, 2019, 09:13:38 pm
FYI, I ventured out and reviewed all sub $0.10 microcontrollers on LCSC. I hope it's somewhat useful:

https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/ (https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/)

I can now confirm that the Padauk MCUs are the best in this segment. We knew this before, did we?

Well, now back to actual projects on the PFS154...

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on August 14, 2019, 03:06:46 am
FYI, I ventured out and reviewed all sub $0.10 microcontrollers on LCSC. I hope it's somewhat useful:
https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/ (https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/)

Great article!  :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on August 18, 2019, 09:46:40 pm
After so many months, I realized I got a message on LCSC from apparently somebody from here asking if I had ever finished my programmer. That remind me of it, and I began yesterday working again on the firmware of the thing.

I have finally got around integrating the software-controlled SMPS and software-emulated USB on the ATtiny84, and most important, get them both working at the same time - to be honest I wasn't really sure if I'd manage to pull this off  ;D

But well, it looks like this tiny AVR is more than capable, and I've finally got Python to talk via libusb to the firmware, and from there command the PFS154 to enter read mode.

Code: [Select]
from usb1 import *
from libusb1 import *
import struct

CMD_START = 1
PDK_READ = 6

ctx = USBContext()
dev = ctx.getByVendorIDAndProductID(0x16C0, 0x05DC)
handle = dev.open()

with handle.claimInterface(0):
    print(handle.getProduct())
    devId, = struct.unpack("h", handle.controlRead(LIBUSB_REQUEST_TYPE_VENDOR, CMD_START, PDK_READ, 0, 2))
    print('Device ID: %03X' % devId)

handle.close()

[attachimg=1]

Instead of loading the whole code to the AVR as the Easy PDK programmer does, which is just not feasible given the mere 512 bytes of RAM, I have several commands which just stream data on demand from/to the microcontroller in program.

The firmware so far is only able to enter a certain mode (ie setup VPP, setup VDD, send command and read and verify response), but it's not yet able to read/write/erase. However, given that the hard part is already done, it should be pretty easy.

The PCB and schematic are available at EasyEDA and are mostly final: https://easyeda.com/socram8888/padauk-programmer
The firmware is still being heavily worked on and it's available on my GitHub: https://github.com/socram8888/PdkProgrammer

[attachimg=2]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 19, 2019, 07:22:51 am
It seems that the upcoming PFS232 will also have a low voltage programming mode (5V). That should greatly simplify building a programmer. Maybe it would be possible to repurpose $2 USBASB clones.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 25, 2019, 10:33:46 am
Hi,
I have build the easy Padauk programmer, the Altium files are attached. it's redesigned in Altium. Note that I have placed a LM258 part for the op-amp since this was the part that was available in my parts.

I have connected it to a PFS173-14pin device, the software recognize the part, But when I try to read, or erase the part I would get errors! do you have any Idea what might be wrong?

(https://img.techpowerup.org/190825/20190825-144724.jpg)

 |O ::) :-[
(https://img.techpowerup.org/190825/untitled.jpg)

Also I want to use the FPPA IDE from Paduak, After compiling some demo project's it would produce  for example T16_Key_LED1.LB0 and T16_Key_LED1.PJ0 in the OBJ folder, which is not a bin nor a hex file, how should I convert the output to hex or bin?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 26, 2019, 12:06:06 pm
Hi,

It looks like this is NOT an EASYPDK programmer. It shows "xProg V1.0" and "www.ASiDesigner.com" on the PCB but no sign of "freepdk" or "easpdkprog".

So most likely this is another thingy which does not violate the CC license from easypdkprog: See https://github.com/free-pdk/easy-pdk-programmer-hardware/blob/master/LICENSE (https://github.com/free-pdk/easy-pdk-programmer-hardware/blob/master/LICENSE)  Section 3 -- License Conditions, a. Attribution, ...

In fact the PCB shows "ASiDesigner (C) 2019", so please contact them for support.

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 27, 2019, 06:09:58 am
Quote
It looks like this is NOT an EASYPDK programmer. It shows "xProg V1.0" and "www.ASiDesigner.com" on the PCB but no sign of "freepdk" or "easpdkprog".
Thanks JS, it's just a redesign and I did it myself, it's for personal use! :)

The software is easpdkprog, only the PCB is changed to fit my needs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 27, 2019, 03:58:24 pm
Hi,

in case EASYPDK programmer reports IC-ID correctly with "probe" command but gives the error message "ERROR: Read failed" or  "ERROR: Write failed" then most likely the voltages VPP / VDD for read/write needs to be adjusted. This can be caused by long wires connecting the IC or a capacitor next to IC VDD or ...

I already optimized read/write voltages a bit more in development branch of the EASYPDK software to compensate extra capacitors / long wires:
https://github.com/free-pdk/easy-pdk-programmer-software/tree/development
(The new EASYPDK software version also requires to flash the new firmware from same development branch).

Regarding the use of PADAUK IDE: Since the IDE creates incompatible PDK files which do have special startup / calibration code inside which need special handling after flashing from PADAUK WRITER it is not possible to use the output and flash with EASYPDKPROG.
Instead you can use the free and open source SDCC compiler to compile your code. SDCC outputs .HEX files which can be used directly with EASYPDKPROG.

Have fun,

JS   
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 28, 2019, 05:53:36 am
Dear JS
Thanks, :-+ I will test it and update in here, Also if it works, you can add my Altium PCB files to the project, so there is more options for hardware design.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 28, 2019, 06:00:20 am
The MCU Firmware is compiling fine, But I can not compile the source code for the windows program! |O

Please note that I have managed to write a simple Hello world program for windows and it can compile! what am I doing wrong that I can not compile the easypdkprog in windows!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on August 28, 2019, 02:41:49 pm
Is there someone willing to sell an assembled programmer for the PMS150C?  Official one seems very unavailable.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 29, 2019, 05:18:11 am
Quote
Is there someone willing to sell an assembled programmer for the PMS150C?  Official one seems very unavailable.
It's open source, you can build it!  ^-^
mine has some issues, if I could solve them I can send you one.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 29, 2019, 10:43:03 am
I have installed Ubuntu on Virtual-box, I'm new to Linux, so how should I compile EASYPDK for windows?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on August 29, 2019, 01:47:19 pm
Quote
Is there someone willing to sell an assembled programmer for the PMS150C?  Official one seems very unavailable.
It's open source, you can build it!  ^-^
mine has some issues, if I could solve them I can send you one.

i appreciate that.  yeah as a last resort ill build one.  if you get it sorted out let me know. 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 30, 2019, 11:14:09 pm
I have installed Ubuntu on Virtual-box, I'm new to Linux, so how should I compile EASYPDK for windows?

Because some people have trouble compiling on/for Windows, I added automatic builds (using travis-ci) to the freepdk github repository.

Every commit will now build the software for all 3 platforms (Linux/Mac/Windows) and check for errors.

Tags will automatically create ZIP files with the compiled binaries for all 3 platforms, available under "releases".

I created a temporary tag "1.1-development" from development branch. Here you can find the 1.1-development (work in progress) binaries for all 3 platforms:
https://github.com/free-pdk/easy-pdk-programmer-software/releases

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on August 31, 2019, 04:46:54 am
Quote
open source hardware programmer: https://github.com/free-pdk/easy-pdk-programmer-hardware

I have checked it, it has only the hardware files, where is the software files for the STM32 MCU and also the PC side software

I just tried to get this board made and it's in a 4x1 panel format, but only one of the boards is populated. Kinda annoying, can this be updated to just be a single non-panelised PCB?
Looks like no original PCB file available?
I don't want to edit the gerber files so I'll just get the panel made as is for testing.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 31, 2019, 05:17:29 am
Quote
Because some people have trouble compiling on/for Windows, I added automatic builds (using travis-ci) to the freepdk github repository.

Every commit will now build the software for all 3 platforms (Linux/Mac/Windows) and check for errors.

Tags will automatically create ZIP files with the compiled binaries for all 3 platforms, available under "releases".

I created a temporary tag "1.1-development" from development branch. Here you can find the 1.1-development (work in progress) binaries for all 3 platforms:
https://github.com/free-pdk/easy-pdk-programmer-software/releases

Have fun,

JS

Thanks JS :-+ :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on August 31, 2019, 06:23:05 am
Quote
open source hardware programmer: https://github.com/free-pdk/easy-pdk-programmer-hardware

I have checked it, it has only the hardware files, where is the software files for the STM32 MCU and also the PC side software

I just tried to get this board made and it's in a 4x1 panel format, but only one of the boards is populated. Kinda annoying, can this be updated to just be a single non-panelised PCB?
Looks like no original PCB file available?
I don't want to edit the gerber files so I'll just get the panel made as is for testing.

Yep, JLC rejected my PCB, Can I get a single PCB gerber files or the original PCB file please? (KiCAD/Eagle/Altium?) Thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on August 31, 2019, 06:44:20 am
Dave, you can find the EasyEDA project here:

https://easyeda.com/tenbaht/schematic

If you open up the PCB layout, looks like you can either edit the panel down to a single PCB and export Gerbers, or export to Altium (folder icon top-left, 'Export', 'Altium') and do it there.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 06:53:54 am
Hi,

I just tried to get this board made and it's in a 4x1 panel format, but only one of the boards is populated. Kinda annoying, can this be updated to just be a single non-panelised PCB?

According to EasyEDA documentation this is the modern way to create a panel: https://docs.easyeda.com/en/PCB/Panelize/index.html
"the panelized file only panelize the board outline. ... Normally, all the PCB factory will support this panelized file, if you not sure, you need to contact your PCB factory support."

The exact same Gerber ZIP file you found was used to produce the 4x1 panel using JLCPCB.com. You can order 5 panels for USD$2 there.

Looks like no original PCB file available?
In case you want to modify the design you can find the complete source schematics/pcb design files in the github repository (look in easyeda folder)


BTW: EasyEDA was used since it is a complete free, easy to use, no installation required PCB editor (very nice for open source projects). It also combines very nice with JLCPCB.com and LCSC.com (right now they are the most affordable source for PCBs and components, which is also a big win for the open source project).


Have fun,

JS 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 07:10:24 am
Yep, JLC rejected my PCB, Can I get a single PCB gerber files or the original PCB file please? (KiCAD/Eagle/Altium?) Thanks.

This is very odd. Several users used the exact same gerber.zip file to order from JLCPCB before and it was accepted.
What was the exact reason for the rejection?

In the mean time I will create a non panelaized Gerber and put it to the github project page.

Edit: https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/pcb also contains a single board gerber now: "Gerber_EASYPDKPROG_PCB12_NoSilk.zip"

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on August 31, 2019, 07:19:52 am
Yep, JLC rejected my PCB, Can I get a single PCB gerber files or the original PCB file please? (KiCAD/Eagle/Altium?) Thanks.

This is very odd. Several users used the exact same gerber.zip file to order from JLCPCB before and it was accepted.
What was the exact reason for the rejection?

It's because the gerber looks like a panel with V score, and they said:
Quote
Sorry to tell you that the size of your panel is too small to be made with v-cut, it needs to 7 *7 cm at least to get through the v-cut machine, could you please kindly check? And you can add edge rail to the the boards as the attachment ,then it can be produced by V-cut ,thank you !

https://imgur.com/KBCX6xg

Quote
In the mean time I will create a non panelaized Gerber and put it to the github project page.
Edit: https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/pcb also contains a single board gerber now: "Gerber_EASYPDKPROG_PCB12_NoSilk.zip"

Thanks!
Looks good this time:

https://imgur.com/254AzHR
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 07:25:54 am
It's because the gerber looks like a panel with V score, and they said:
Quote
Sorry to tell you that the size of your panel is too small to be made with v-cut, it needs to 7 *7 cm at least to get through the v-cut machine, could you please kindly check? And you can add edge rail to the the boards as the attachment ,then it can be produced by V-cut ,thank you !

Thanks for the feedback. It looks like JLCPCB changed the rules recently (New: v-cut panel must be >= 7x7cm now) . A week ago I ordered some other PCBs and my panel was much smaller.

JS

Edit: I updated the panel version to have the rails on the side so the resulting panel matches the new "panel >= 7x7cm" rule.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 31, 2019, 08:10:54 am
Dave you can check out my Altium project!

JS, I have compiled the ARM program and flashed the easyPaduk, but unfortunately it says the firmware is a mismatch! (I have flashed the programmer with the new Bin file) also can you please update the make file for the PC side software to generate the .exe file for windows too( I mean inside ubuntu)

(https://img.techpowerup.org/190831/untitled.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 31, 2019, 08:11:31 am
I ordered directly out of easyeda about three weeks ago and had no issue at all.
Got 5 pcbs from JLPCB.

One thing I noticed: I would suggest changing all the text to silk screen. It's quite hard to read on a blue pcb.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on August 31, 2019, 08:17:14 am
Dave you can check out my Altium project!

IIRC you didn't get it working or had some issue with it?
I went with JS's gebers for now because it's been reported working, I just want to get it up and running for a video with the least fuss.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 08:45:57 am
Hi,

JS, I have compiled the ARM program and flashed the easyPaduk, but unfortunately it says the firmware is a mismatch! (I have flashed the programmer with the new Bin file)

Can it be that you compiled the firmware from master branch? The development version also needs the firmware from development branch. There is a pre compiled "EASYPDKPROG.dfu" in the firmware directory of development branch. I just checked and it works 100% correct.
DEVELOPMENT FIRMWARE FOR DEVELOPMENT EASYPDKPROG: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Firmware

also can you please update the make file for the PC side software to generate the .exe file for windows too( I mean inside ubuntu)

The same makefile is used also for cross compiling. You need to set the correct environment variables in order to use Ubuntu to cross compile for windows.
You can have a look in the .travis files in the development branch. All settings are there. On Ubuntu, at minimum, you have to install the mingw package, and set the following environment variables:

Install:
sudo apt install gcc-mingw-w64-i686

Compile:
export OSTYPE=msys
export host_alias=i686-w64-mingw32
export CC=i686-w64-mingw32-gcc
export STRIP=i686-w64-mingw32-strip

make

mv easypdkprog easypdkprog.exe


A more easy way to compile for Windows is to install "MSYS2" on Windows and use the MinGW shell.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 31, 2019, 10:54:09 am
Thanks JS, I managed to flash the Dev branch to the ARM and now it's working, But still only probing is working |O |O |O any Idea what might goes wrong?

(https://img.techpowerup.org/190831/untitled.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 12:54:21 pm
Thanks JS, I managed to flash the Dev branch to the ARM and now it's working, But still only probing is working |O |O |O any Idea what might goes wrong?

Now you have to check your hardware variant. On the picture I saw that C1 is not populated and also Y1 is missing. A cap on the 15V rail is essential since VCC/VDD draw some power during programing. The crystal is used to get better tuning results after the CPU is flashed, without it the drift might be much higher or you create a very special clock path using the HSI48 with sync to USB frames (then programmer can not be used stand alone - a feature planned for future use, just like WRITER).

Also, since you changed the opamp, it might be possible that the output voltages differ. You can use the "easypdkprogtest" program to check that the output voltage is correct:

DO THIS WITHOUT A MCU CONNECTED TO THE PROGRAMMER

make easypdkprogtest

./easypdkprogtest
vdd: 5.01   vpp: 4.98    (vref= 3.30)


Please check that VDD and VPP are 5V and VREF is 3.3V. Also measure them on your PCB.

In case VDD and VPP voltages are incorrect you need to tune the DAC reference values for your specific hardware (in fpdk.c you need to change FPDK_VDD_DAC_MAX_MV / FPDK_VPP_DAC_MAX_MV).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 31, 2019, 02:24:47 pm
FYI, I just finished my own built of the easypdk programmer. I built up two PCBs and they both work without a hitch, even though i manually soidered... Very good job, js!

There was one bizarre isseue with MSYS when compiling the command line tool. I had to change the line "CC ?= GCC" in the makefile to "CC = GCC". Not sure what is going on, because i know that the ?= directive works in other makefiles i use.

I still have PCBs and components for three more programmers left. If somebody in Germany is interested, I would donate them.

Building up the PCB was not that easy. Too many small components. To allows easier access for other people it may be helpful to have a version with fewer components or identify an option of having the pcb populated by some company.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 31, 2019, 06:28:04 pm
Hi,

To understand the register mappings on different PDK CPU types better I created a list (based on include files from original IDE).

https://github.com/free-pdk/fppa-pdk-documentation/blob/master/PDK_register_mapping_scroll_right.csv

Attached is a colorful version as PNG from it.

Based on this info (most registers jump around for different types and only a few number remains static) I think the best idea would be to create one include file per supported processor like:

pdk/pmc150c.h
pdk/pfs154.h
pdk/pfs173.h
...

I fully agree with this approach. I wonder, has anybody already been looking into this? Right now, I am cleaning up some of my old examples.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 31, 2019, 07:01:07 pm
Hi,

To understand the register mappings on different PDK CPU types better I created a list (based on include files from original IDE).

https://github.com/free-pdk/fppa-pdk-documentation/blob/master/PDK_register_mapping_scroll_right.csv

Attached is a colorful version as PNG from it.

Based on this info (most registers jump around for different types and only a few number remains static) I think the best idea would be to create one include file per supported processor like:

pdk/pmc150c.h
pdk/pfs154.h
pdk/pfs173.h
...

I fully agree with this approach. I wonder, has anybody already been looking into this? Right now, I am cleaning up some of my old examples. So far I have defined everything in line.

I'm working on it. Right now I work on a PMS150C based project and created a full include file for it. Right now I wait for PCB delivery. As soon as it's done I will put the project online.
Fixing the PDK13 bit SDCC compiler was one of the time consuming tasks, but now it seems to be very stable (same as for PDK14/PDK15).

JS

work in progress:

pms150c.h
Code: [Select]
#ifndef __PMS150C_H__
 #define __PMS150C_H__

 #include "pdkcommon.h"

//set calibration macros
 #define EASY_PDK_CALIBRATE_IHRC EASY_PDK_CALIBRATE_IHRC_H8
 #define EASY_PDK_CALIBRATE_ILRC EASY_PDK_CALIBRATE_IHRC_L8

//IO register definitions
//__sfr __at(0x00) _flag;
//0x01
//__sfr __at(0x02) _sp;
__sfr __at(0x03) _clkmd;
__sfr __at(0x04) _inten;
__sfr __at(0x05) _intrq;
__sfr __at(0x06) _t16m;
//0x07
//0x08
__sfr __at(0x09) _tm2b;
__sfr __at(0x0a) _eoscr;
__sfr __at(0x0b) _ihrcr;
__sfr __at(0x0c) _integs;
__sfr __at(0x0d) _padier;
//0x0e
//0x0f
__sfr __at(0x10) _pa;
__sfr __at(0x11) _pac;
__sfr __at(0x12) _paph;
//0x13
//0x14
//0x15
//0x16
__sfr __at(0x17) _tm2s;
//0x18
__sfr __at(0x19) _bgtr;
__sfr __at(0x1a) _gpcc;
__sfr __at(0x1b) _misc;
__sfr __at(0x1c) _tm2c;
__sfr __at(0x1d) _tm2ct;
__sfr __at(0x1e) _gpcs;
__sfr __at(0x1f) _ilrcr;

//T16C register
__sfr16          _t16c;

//clkmd definitions
 #define CLKMD_ENABLE_PA5RST          0x01
 #define CLKMD_ENABLE_WATCHDOG        0x02
 #define CLKMD_ENABLE_ILRC            0x04
 #define CLKMD_ENABLE_IHRC            0x10
 #define CLKMD_IHRC_DIV2              0x20
 #define CLKMD_IHRC_DIV4              0x00
 #define CLKMD_IHRC_DIV8              0x28
 #define CLKMD_IHRC_DIV16             0x08
 #define CLKMD_IHRC_DIV32             0x68
 #define CLKMD_IHRC_DIV64             0x88
 #define CLKMD_ILRC                   0xe0
 #define CLKMD_ILRC_DIV4              0xc0

//interrupt enable definitions
 #define INTEN_PA0                    0x01
 #define INTEN_T16                    0x04
 #define INTEN_COMP                   0x10
 #define INTEN_TM2                    0x40

//interrupt request definitions
 #define INTRQ_PA0                    0x01
 #define INTRQ_T16                    0x04
 #define INTRQ_COMP                   0x10
 #define INTRQ_TM2                    0x40

//tm16 definitions
 #define T16_INTSRC_8BIT              0x00
 #define T16_INTSRC_9BIT              0x01
 #define T16_INTSRC_10BIT             0x02
 #define T16_INTSRC_11BIT             0x03
 #define T16_INTSRC_12BIT             0x04
 #define T16_INTSRC_13BIT             0x05
 #define T16_INTSRC_14BIT             0x06
 #define T16_INTSRC_15BIT             0x07
 #define T16_CLK_DIV1                 0x00
 #define T16_CLK_DIV4                 0x08
 #define T16_CLK_DIV16                0x10
 #define T16_CLK_DIV64                0x18
 #define T16_CLK_DISABLE              0x00
 #define T16_CLK_SYSCLK               0x20
 #define T16_CLK_PA4_FALL             0x60
 #define T16_CLK_IHRC                 0x80
 #define T16_CLK_ILRC                 0xC0
 #define T16_CLK_PA0_FALL             0xE0

//eosc definitions
 #define EOSC_LVD_BANDGAP_SHUTDOWN    0x01

//integs definitions
 #define INTEGS_PA0_BOTH              0x00
 #define INTEGS_PA0_RISING            0x01
 #define INTEGS_PA0_FALLING           0x02
 #define INTEGS_T16_RISING            0x00
 #define INTEGS_T16_FALLING           0x04
 #define INTEGS_COMP_BOTH             0x00
 #define INTEGS_COMP_RISING           0x40
 #define INTEGS_COMP_FALLING          0x80

//padie definitions
 #define PADIE_PA0_WAKEUP_ENABLE      0x01
 #define PADIE_PA3_WAKEUP_ENABLE      0x08
 #define PADIE_PA4_WAKEUP_ENABLE      0x10
 #define PADIE_PA5_WAKEUP_ENABLE      0x20
 #define PADIE_PA6_WAKEUP_ENABLE      0x40
 #define PADIE_PA7_WAKEUP_ENABLE      0x80

//misc definitions
 #define MISC_WATCHDOG_8K_ILRC        0x00
 #define MISC_WATCHDOG_16K_ILRC       0x01
 #define MISC_WATCHDOG_64K_ILRC       0x02
 #define MISC_WATCHDOG_256K_ILRC      0x03
 #define MISC_LVR_DISABLE             0x04
 #define MISC_FAST_WAKEUP_ENABLE      0x20

//tm2c definitions
 #define TM2C_CLK_DISABLE             0x00
 #define TM2C_CLK_SYSCLK              0x10
 #define TM2C_CLK_IHRC                0x20
 #define TM2C_CLK_EOSC                0x30
 #define TM2C_CLK_ILRC                0x40
 #define TM2C_CLK_COMPOUT             0x50
 #define TM2C_CLK_PA0_RISE            0x80
 #define TM2C_CLK_PA0_FALL            0x90
 #define TM2C_CLK_PB0_RISE            0xA0
 #define TM2C_CLK_PB0_FALL            0xB0
 #define TM2C_CLK_PA4_RISE            0xC0
 #define TM2C_CLK_PA4_FALL            0xD0
 #define TM2C_OUT_DISABLE             0x00
 #define TM2C_OUT_PB2                 0x04
 #define TM2C_OUT_PA3                 0x08
 #define TM2C_OUT_PB4                 0x0C
 #define TM2C_MODE_PERIOD             0x00
 #define TM2C_MODE_PWM                0x02
 #define TM2C_INVERT_OUT              0x01

//tm2s definitions
 #define TM2S_PWM_RES_8BIT            0x00
 #define TM2S_PWM_RES_6BIT            0x80
 #define TM2S_PRESCALE_NONE           0x00
 #define TM2S_PRESCALE_DIV4           0x20
 #define TM2S_PRESCALE_DIV16          0x40
 #define TM2S_PRESCALE_DIV64          0x60

//gpcc definitions
 #define GPCC_COMP_PLUS_VINT          0x00
 #define GPCC_COMP_PLUS_PA4           0x01
 #define GPCC_COMP_MINUS_PA3          0x00
 #define GPCC_COMP_MINUS_PA4          0x02
 #define GPCC_COMP_MINUS_BANDGAP_1V2  0x04
 #define GPCC_COMP_MINUS_VINT_R       0x06
 #define GPCC_COMP_MINUS_PA6          0x08
 #define GPCC_COMP_MINUS_PA7          0x0A

//gpcs definitions
 #define GPCS_COMP_CASE1              0x00
 #define GPCS_COMP_CASE2              0x10
 #define GPCS_COMP_CASE3              0x20
 #define GPCS_COMP_CASE4              0x30
 #define GPCS_COMP_WAKEUP_ENABLE      0x40
 #define GPCS_COMP_OUTPUT_PA0         0x80

 //__PMS150C_H__


pdkcommon.h
Code: [Select]
#ifndef __PDKCOMMON_H__
 #define __PDKCOMMON_H__

//macros so we can use defines in assembler strings
 #define _STRINGIFY(x)
 #define _ASMV(x) "_"_STRINGIFY(x)
 #define _ASMD(x) _STRINGIFY(x)

//definitions for built in opcodess
 #define __engint()  __asm__("engint\n")
 #define __disgint() __asm__("disgint\n")
 #define __stopsys() __asm__("stopsys\n")
 #define __stopexe() __asm__("stopexe\nnop\n")
 #define __set0(x,y)  __asm__("set0 "_ASMV(x)", #"_ASMD(y)"\n")
 #define __set1(x,y)  __asm__("set1 "_ASMV(x)", #"_ASMD(y)"\n")

//macros for clock setup
 #define EASY_PDK_INIT_SYSCLOCK_8MHZ()   {_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV2;}
 #define EASY_PDK_INIT_SYSCLOCK_4MHZ()   {_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV4;}
 #define EASY_PDK_INIT_SYSCLOCK_2MHZ()   {_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV8;}
 #define EASY_PDK_INIT_SYSCLOCK_1MHZ()   {_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV16;}
 #define EASY_PDK_INIT_SYSCLOCK_512kHz() {_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV32;}

//place holder for EASYPDK serial inserted from easypdkprog
 #define EASY_PDK_SERIAL(sname) static const uint8_t sname[8] = {'F','P','S','E','R','I','A','L'}

//place holder for EASYPDK calibrations executed / replaced by easypdkprog
 #define EASY_PDK_CALIBRATE_IHRC_H8(frequency,millivolt) \
__asm__(                      \
  "and a, #'H'                \n"\
  "and a, #'8'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
  "and a, #("#millivolt")     \n"\
  "and a, #("#millivolt">>8)  \n"\
)

 #define EASY_PDK_CALIBRATE_ILRC_L8(frequency,millivolt) \
__asm__(                      \
  "and a, #'L'                \n"\
  "and a, #'8'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
  "and a, #("#millivolt")     \n"\
  "and a, #("#millivolt">>8)  \n"\
)
 #define EASY_PDK_CALIBRATE_IHRC_H9(frequency,millivolt) \
__asm__(                      \
  "and a, #'H'                \n"\
  "and a, #'9'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
  "and a, #("#millivolt")     \n"\
  "and a, #("#millivolt">>8)  \n"\
  "and a, #0                  \n"\
)

 #define EASY_PDK_CALIBRATE_ILRC_L9(frequency,millivolt) \
__asm__(                      \
  "and a, #'L'                \n"\
  "and a, #'9'                \n"\
  "and a, #("#frequency")     \n"\
  "and a, #("#frequency">>8)  \n"\
  "and a, #("#frequency">>16) \n"\
  "and a, #("#frequency">>24) \n"\
  "and a, #("#millivolt")     \n"\
  "and a, #("#millivolt">>8)  \n"\
  "and a, #0                  \n"\
)

 //__PDKCOMMON_H__


example main.c
Code: [Select]
#include <stdint.h>
 #include "pms150c.h"

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_8MHZ();              //use 8MHz to save power
  EASY_PDK_CALIBRATE_IHRC(8000000,3300);      //tune SYSCLK to 8.0MHz @ 3.300V
  return 0;                                   //perform normal initialization
}

void main(void)
{
  for(;;)
  {
     //YOUR CODE HERE
  }
}

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 01, 2019, 06:07:39 am
Dear JS
Thanks for help and support,
I could not compile the code on ubuntu with the commands that you said! :-X :-X :-X

But I managed to install MSYS2 on my machine and finally it could compile the code, But there is something very weird! the code just does not run |O |O |O also I could compile the easypdkprogtest program too, but It can not run either!

See these pictures? what's going on wrong? the size of easypdkprog.exe that is compiled on my machine with MSYS2 is 55.5KB,but your compiled version is about 79KB

The MSYS2 compile output
(https://img.techpowerup.org/190901/1.jpg)

when I run the code, it just hangs and do nothing, so I should close it with ctrl + C
(https://img.techpowerup.org/190901/2.jpg)

Also when I try to run it from command prompt it says some missing MSYS2 DLL |O
(https://img.techpowerup.org/190901/3.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 01, 2019, 06:37:25 am
Well, did you try to locate msys2.dll? It appears that you are trying to execute easypdkprog by starting it from the explorer. Try starting it from the MSYS shell. Only then the proper path is set.

Btw - i used mingw32/msys1 to compile the exe and had no issues. I had problems with mingw64 in the past.

Why don't you use the binaries provided by js? They work well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 01, 2019, 07:57:25 am
But I managed to install MSYS2 on my machine and finally it could compile the code, But there is something very weird! the code just does not run |O |O |O also I could compile the easypdkprogtest program too, but It can not run either!

I said you should use the MinGW shell (from MSYS2) to compile (look in your start menu, the MSYS2 installer has created MSys2 Shell and MinGW Shell shortcuts).

Your MSYS2 compile looks fine and it also will work. You only need to use it in standard Windows CMD-Prompt (you can not run it from MSys2 Shell). You also need to copy the MSYS-2.0.DLL to the same directory as easypdkprog.exe (or to Windows system directory).

In case you use MinGW shell the resulting exe file will be smaller and there will be no dependency to any DLL which is not already present on a standard Windows installation (That's why I still prefer MinGW for compiling).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 01, 2019, 08:29:56 am
Thanks JS, Now the program would run from the MSYS2 shell, The voltages are a bit high

(https://img.techpowerup.org/190901/untitled.jpg)
They are 5.17v and 5.18v with my voltmeter, are they in expected range?how should I calculate the offset and change.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 01, 2019, 09:39:17 am
Thanks JS, Now the program would run from the MSYS2 shell, The voltages are a bit high
They are 5.17v and 5.18v with my voltmeter, are they in expected range?how should I calculate the offset and change.

The voltages look indeed a bit high, which most likely cause the problems you have.

ADC is working good since it detected the voltage to be 5.16V (you measured 5.17V/5.18V) => Maybe I will add a self calibration later.

For you now the easiest way is to do the following:

1. change source code of easypdkprogtest.c  and put 2 times "100.0" instead of "5.0" as requested output voltage (Don't worry, it can output max 15V):

  //be carefully, remove IC from programmer!
  FPDKCOM_SetOutputVoltages(comfd, 100.0, 100.0);


compile and run it, then write down the reported voltages:

./easypdkprogtest
vdd: 6.29   vpp: 13.30    (vref= 3.30)   


This are the maximum voltages the hardware can produce (for standard easypdk programmer):
VDD: 6.29 V = 6290 mV
VPP: 13.30 V = 13300 mV

2. go to firmware source, file "fpdk.c" an change the values of the DAC reference voltage:

//board specific max values (DAC max => mV max after opamp output / -30 mV DAC DC offset)
#define FPDK_VDD_DAC_MAX_MV ( 6290 - 30)
#define FPDK_VPP_DAC_MAX_MV (13300 - 30)


3. compile and flash firmware

4. change back easypdkprogtest to 2 times 5.0V and check output

It should now report 5.0V for VDD and VPP.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 01, 2019, 07:52:30 pm
I spent some time tinkering with a toolchain setup for SDCC and easypdkprog. You can find my work in progress here:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain

Notable findings:

Includes
- I wrote a small python script that automatically generates include files from the CSV that JS posted a while ago. This should greatly reduce the work of creating include files for all MCUS. you can find it at
https://github.com/cpldcpu/SimPad/tree/master/Toolchain/util
- The goal is currently to have one master "io.h" file that automatically includes the architecture specific files.
- The architecture specific includes contain information about i/o register locations. The descriptions of the individual bits seem to be universial for all devices and have therefore been moved into a common file.
- I also introduced F_CPU to allow for a proper delay function.

Makefile
- Unversial makefile added, based on STM8-bare-min. Everything is automated now.

SDCC
- I was pleasantly surprised to learn that SDCC can infer SET0/SET1 now. Therefore it is not necessary to introduce specific macros for set0/set1
- Since SDCC implements a very unusual way of defining SFRs, intellisense/vscode is not able to identify the register definitions. This is somewhat unfortunate. There is an open ticked about this at the vscode github since last year, but apparently it is not a priority. Is there any workaround? Doing it like AVR-GCC ("__sfr(register)") would allow using defines, which is more compatible to intellisense.
- It does not seem to be possible to use local labels in inline assembler? This is inconvenient because it does not allow inlining of functions with assembler code when they use labels...
- It appears the -p options is not yet supported for the PDK architecture? This would be very useful, because it would allow distinguishing different processors from the makefile. May use a define as a workaround for now...

Easypdkprog
 does not write the last byte of the ihx for some reason. This is only noticable when linking several files. Already submitted an issue.

I will add more examples soon. Also planning to integrates JS autocalibration code.

Let me know what you think. There are still many things to be clarified regarding naming etc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 01, 2019, 10:59:03 pm
So I have mostly given up on getting the programmer running on the ATtiny - it's just not capable of doing so much realtime stuff at once - either you break USB, or you break the SMPS regulation, you can't have both at once.

Therefore, I have switched to plan B - using an Arduino as development platform instead. And it turns out this is probably the way I should have chosen from the start.

While certainly not the most professional-looking alternative, it sure is the easiest to build. It uses as little components as possible.

The schematic is attached, and the firmware along with upload scripts can be found in https://github.com/socram8888/ArduinoPDKProgrammer. This already supports uploading and verifying IHX files, as those generated by SDCC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 01, 2019, 11:23:53 pm
@tim_: I have used your blinkyasm example for testing my programmer. However, while the LED turns ON, it never turns back off. I've tried commenting out the wait busy loop and I can see now with the scope the GPIO toggling. Could you tell me if the IHX file you are getting for that matches mine?

Code: [Select]
:20000000022F8201782F8301012F9101101E101C0630FF2F820B830B82110C3083110C30C7
:020020007A0064
:00000001FF

I have just compiled it using the SDCC snapshot for today (1st September 2019), so I am not sure if the compilation is broken.

My other guessing is that the SRAM is bad in this chip (hence the DCSN never reaches zero to leave). Has anybody else experienced something like this in its Padauk IC, where the CPU is indeed working but the SRAM is dead?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 02, 2019, 05:53:29 am
I spent some time tinkering with a toolchain setup for SDCC and easypdkprog. You can find my work in progress here:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain

Notable findings:

Includes
- I wrote a small python script that automatically generates include files from the CSV that JS posted a while ago. This should greatly reduce the work of creating include files for all MCUS. you can find it at
https://github.com/cpldcpu/SimPad/tree/master/Toolchain/util
- The goal is currently to have one master "io.h" file that automatically includes the architecture specific files.
- The architecture specific includes contain information about i/o register locations. The descriptions of the individual bits seem to be universial for all devices and have therefore been moved into a common file.
- I also introduced F_CPU to allow for a proper delay function.

Makefile
- Unversial makefile added, based on STM8-bare-min. Everything is automated now.

SDCC
- I was pleasantly surprised to learn that SDCC can infer SET0/SET1 now. Therefore it is not necessary to introduce specific macros for set0/set1
- Since SDCC implements a very unusual way of defining SFRs, intellisense/vscode is not able to identify the register definitions. This is somewhat unfortunate. There is an open ticked about this at the vscode github since last year, but apparently it is not a priority. Is there any workaround? Doing it like AVR-GCC ("__sfr(register)") would allow using defines, which is more compatible to intellisense.
- It does not seem to be possible to use local labels in inline assembler? This is inconvenient because it does not allow inlining of functions with assembler code when they use labels...
- It appears the -p options is not yet supported for the PDK architecture? This would be very useful, because it would allow distinguishing different processors from the makefile. May use a define as a workaround for now...

Easypdkprog
 does not write the last byte of the ihx for some reason. This is only noticable when linking several files. Already submitted an issue.

I will add more examples soon. Also planning to integrates JS autocalibration code.

Let me know what you think. There are still many things to be clarified regarding naming etc.

I think auto generating the IO header files is not the way to go.
The most work was to add all the bit definitions for the specific IO registers (see "pms150.h" from above).
This is needed to do simple things like: _clkmd=CLKMD_ENABLE_ILRC | CLKMD_ENABLE_IHRC | CLKMD_IHRC_DIV2;

Also since SDCC defines "_sp" and "_flags" internally I think we should keep the "_" prefix for all other registers as well

I also created a Makefile similar to yours. I will release it with the project as soon as the PCBs arrived and I testes everything

The last byte missing problem from easypdkprog seems odd and it does not happen to me. Maybe programming the last byte was not working on your hardware and some tweaking of the code is required to make this more reliable.

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 02, 2019, 05:59:25 am
Dear JS
Thanks for the feedback, the output is now fine, it will produce exactly 5.0V, But Still I can probe and detect the PFS173,But reading, flashing etc fails!
though I found something weird! when I measured the VDD and VPP with this command

//be carefully, remove IC from programmer!
FPDKCOM_SetOutputVoltages(comfd, 100.0, 100.0);

(https://img.techpowerup.org/190902/untitled.jpg)

The output was swamped, I mean I could measure the VPP to be 13.7V and the VDD to be 6.45V with my Multi-meter, but in the terminal it was the other way around!
I double checked the schematic to see if I have connected the DAC's on my PCB swapped, But it was like your schematic!
I have attached my schematic and it's exactly like easyPDK hardware in the DAC part.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 02, 2019, 06:23:09 am
Dear JS, I have found one bug in my schematic, the ADC channels are swapped in my Design |O :palm:, so what should I change in the software to correct it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 02, 2019, 06:32:00 am
Hi,

your output does indeed look wrong. Maybe you swapped ADC input lines on STM32? If so you can change the readout in software: "fpdk.c", in function "_FPDK_ADC_HandleData", in the for loop swap "avpp" and "avdd" (swap them in the for loop only).

On the other hand the analog values are not used (yet). They are there for future use like auto calibration of VDD and VPP and to read out protected ICs.

Next you need to do: Monitor VPP / VDD with a scope during READ / WRITE. Maybe your capacitors do not match and you have instabilities or noise. BTW did you put C1 yet?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 06:32:10 am
@tim_: I have used your blinkyasm example for testing my programmer. However, while the LED turns ON, it never turns back off. I've tried commenting out the wait busy loop and I can see now with the scope the GPIO toggling. Could you tell me if the IHX file you are getting for that matches mine?

Code: [Select]
:20000000022F8201782F8301012F9101101E101C0630FF2F820B830B82110C3083110C30C7
:020020007A0064
:00000001FF

I have just compiled it using the SDCC snapshot for today (1st September 2019), so I am not sure if the compilation is broken.

My other guessing is that the SRAM is bad in this chip (hence the DCSN never reaches zero to leave). Has anybody else experienced something like this in its Padauk IC, where the CPU is indeed working but the SRAM is dead?

See disassembly of your hex file below. For some reason it is missing calls to the delay routine?!?

I would suggest you use the blinky example from the toolchain folder, as posted above. Also, always check *.asm files or use the dissembler to double check. The old examples heavily rely on workarounds to be able to cope with bugs in  the very early versions of SDCC. I will remove them soon.

Code: [Select]
0000: 2F02 mov A,#$02
0001: 0182 movio $02,A
0002: 2F78 mov A,#$78
0003: 0183 movio $03,A
0004: 2F01 mov A,#$01
0005: 0191 movio $11,A
0006: 1E10 set1io $10,#0
0007: 1C10 set0io $10,#0
0008: 3006 goto $0006
0009: 2FFF mov A,#$FF
000A: 0B82 mov $02,A
000B: 0B83 mov $03,A
000C: 1182 dzsn $02
000D: 300C goto $000C
000E: 1183 dzsn $03
000F: 300C goto $000C
0010: 007A ret
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 06:50:00 am

I think auto generating the IO header files is not the way to go.
The most work was to add all the bit definitions for the specific IO registers (see "pms150.h" from above).
This is needed to do simple things like: _clkmd=CLKMD_ENABLE_ILRC | CLKMD_ENABLE_IHRC | CLKMD_IHRC_DIV2;

Well, the thinking here is very simple: Padauk seems to reuse specific peripheral modules, but moves them around in the I/O space. The description of the individual registers can be done once on a common file, this does not need to be auto generated. To cope with padauk moving around peripheral modules in the address space, it is very convenient to auto generate the register addresses. This also makes global renaming much easier.

Also since SDCC defines "_sp" and "_flags" internally I think we should keep the "_" prefix for all other registers as well

yeah, I was unsure about this. There does not seem to be any general convention for SFR naming. SDCC also uses the _xxx naming for internal variable names in SRAM, so it seems to be a bit confusing to use the same conventions for memory and SFR. I guess the _ prefix is added to avoid namespace collisions.

AVR-GCC, PIC-Utils and the STM8-libs (both official and unofficiel) all use no prefix and capital letters for SFR naming. Maybe that is the way to go? (e.g. PA, PAC)


The last byte missing problem from easypdkprog seems odd and it does not happen to me. Maybe programming the last byte was not working on your hardware and some tweaking of the code is required to make this more reliable.

Well, it exactly follows your build and the the device was directly plugged into the header, no long cables. The issue is 100% reproducible. I will try more devices.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 07:05:36 am
So I have mostly given up on getting the programmer running on the ATtiny - it's just not capable of doing so much realtime stuff at once - either you break USB, or you break the SMPS regulation, you can't have both at once.

Therefore, I have switched to plan B - using an Arduino as development platform instead. And it turns out this is probably the way I should have chosen from the start.

While certainly not the most professional-looking alternative, it sure is the easiest to build. It uses as little components as possible.

The schematic is attached, and the firmware along with upload scripts can be found in https://github.com/socram8888/ArduinoPDKProgrammer. This already supports uploading and verifying IHX files, as those generated by SDCC.

Very nice work! It appears that all new flash MCUs from Padauk will also support 5V programming. (See low voltage programming section in the datasheets). Hopefully that means that it will be possible to build a programmer from an Arduino without adding any additional circuitry for voltage control. This would allow much easier access to a programmer. Although I would not be surprised if they still used analog voltages control schemes to enter programming mode... we'll see.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 02, 2019, 07:53:08 am
I think auto generating the IO header files is not the way to go.

The most work was to add all the bit definitions for the specific IO registers (see "pms150.h" from above).
This is needed to do simple things like: _clkmd=CLKMD_ENABLE_ILRC | CLKMD_ENABLE_IHRC | CLKMD_IHRC_DIV2;
It should be possible to just ship the header files with SDCC (this already happens for some MCS-51 derivatives and some HC08 devices). They would live in device/include/pdk13, device/include/pdk14, device/include/pdk15.
Quote

Also since SDCC defines "_sp" and "_flags" internally I think we should keep the "_" prefix for all other registers as well

On the other hand, the stack pointer and flags are special: In typical programs they will be handled entirely by the compiler, while the others would be handled by the user program (also we have one stack pointer and flag register per FPPA, while the other registers are shared across all FPPA).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 02, 2019, 07:57:00 am
yeah, I was unsure about this. There does not seem to be any general convention for SFR naming. SDCC also uses the _xxx naming for internal variable names in SRAM, so it seems to be a bit confusing to use the same conventions for memory and SFR. I guess the _ prefix is added to avoid namespace collisions.

SDCC prefixes every symbol X in C by _ to get a symbol _X for asm (so this affects both variable names and function names, no matter where the objects reside).

Philipp

P.S.: This implies that the name, to be usable from C, has to be _-prefixed in asm.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 02, 2019, 08:12:02 am
Well, the thinking here is very simple: Padauk seems to reuse specific peripheral modules, but moves them around in the I/O space. The description of the individual registers can be done once on a common file, this does not need to be auto generated. To cope with padauk moving around peripheral modules in the address space, it is very convenient to auto generate the register addresses. This also makes global renaming much easier.

Unfortunately this is not entirely true. On some MCUs some functions (bits) inside of the peripheral modules do have different meanings.
Examples: Interrupt Enable/Request register, CLKMD register, TIMER register, ...

That's why I decided to do one file per MCU.

BTW: I think in reality only a hand full of MCU's will be popular, so not many include files are needed. And if somebody needs one for a specific MCU, adaption is easy, when you only need to copy an existing file and modify it according to the data sheet.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 02, 2019, 09:16:41 am
Quote
BTW did you put C1 yet?!
What C1? do you mean a cap on VCC and GND and the PFS173? something like this?
Also I have connected VPP to PA5 or RST pin, is it correct?
(https://img.techpowerup.org/190902/20190902-130608.jpg)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 02, 2019, 10:44:58 am
See disassembly of your hex file below. For some reason it is missing calls to the delay routine?!?
Sorry, I had removed call to see if a loop without any call worked fine (which it did, it worked and I could see the pin toggling on a scope) and forgot to recompile to paste it here.

This is it with the call:
Code: [Select]
:20000000022F8201782F8301012F9101101E0B38101C0B380630FF2F820B830B82110E300F
:0600200083110E307A008E
:00000001FF

I am getting the following disassembly:
Code: [Select]
0000:   2F02    mov     A,#$02
0001:   0182    movio   $02,A
0002:   2F78    mov     A,#$78
0003:   0183    movio   $03,A
0004:   2F01    mov     A,#$01
0005:   0191    movio   $11,A
0006:   1E10    set1io  $10,#0
0007:   380B    call    $000B
0008:   1C10    set0io  $10,#0
0009:   380B    call    $000B
000A:   3006    goto    $0006
000B:   2FFF    mov     A,#$FF
000C:   0B82    mov     $02,A
000D:   0B83    mov     $03,A
000E:   1182    dzsn    $02
000F:   300E    goto    $000E
0010:   1183    dzsn    $03
0011:   300E    goto    $000E
0012:   007A    ret

It looks fine, but I had to adjust the assembler (change "SDAS=sdaspdk" to "SDAS=sdaspdk14") so I'm not sure if anything else could have gotten broken.

I would suggest you use the blinky example from the toolchain folder, as posted above. Also, always check *.asm files or use the dissembler to double check. The old examples heavily rely on workarounds to be able to cope with bugs in  the very early versions of SDCC. I will remove them soon.
Okay, I will try this evening with the ones from toolchain, and using another IC to rule out that the chip is damaged. Many thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 02, 2019, 02:53:37 pm
Quote
BTW did you put C1 yet?!
What C1? do you mean a cap on VCC and GND and the PFS173? something like this?

I mean C1 on your programmer board (I think it is for the high voltage output). Also Y1 (the oscillator) was missing in the picture from you. Did you change the firmware to use the HSI48 clock source instead of the external OSC?

The cap you added on the PADAUK MCU is contra productive since it might require different timing for VPP / VDD phase of programming (remove it for testing).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 03:54:52 pm
See disassembly of your hex file below. For some reason it is missing calls to the delay routine?!?
Sorry, I had removed call to see if a loop without any call worked fine (which it did, it worked and I could see the pin toggling on a scope) and forgot to recompile to paste it here.

This is it with the call:
Code: [Select]
:20000000022F8201782F8301012F9101101E0B38101C0B380630FF2F820B830B82110E300F
:0600200083110E307A008E
:00000001FF

I am getting the following disassembly:


Ah ok, that explain.

Well, from your description the issue could be explained by corruption of the last instruction during writing. You could add some dummy instructions to the end of the program (nops) to check.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 02, 2019, 06:46:55 pm
I am getting the following disassembly:
Code: [Select]
0000:   2F02    mov     A,#$02
0001:   0182    movio   $02,A
0002:   2F78    mov     A,#$78
0003:   0183    movio   $03,A
0004:   2F01    mov     A,#$01
0005:   0191    movio   $11,A
0006:   1E10    set1io  $10,#0
0007:   380B    call    $000B
0008:   1C10    set0io  $10,#0
0009:   380B    call    $000B
000A:   3006    goto    $0006
000B:   2FFF    mov     A,#$FF
000C:   0B82    mov     $02,A
000D:   0B83    mov     $03,A
000E:   1182    dzsn    $02
000F:   300E    goto    $000E
0010:   1183    dzsn    $03
0011:   300E    goto    $000E
0012:   007A    ret

For me it looks like you trash your stack...

This sets the SP to point to memory location #2
0000:   2F02    mov     A,#$02
0001:   0182    movio   $02,A
...
The call will put the return address at SP (memory location #2 and #3, SP will point to #4 when call is executed)
0007:   380B    call    $000B
...
In the function you overwrite memory location #2,#3 (the return address)
000B:   2FFF    mov     A,#$FF
000C:   0B82    mov     $02,A
000D:   0B83    mov     $03,A
...
Both decrements will have 0 as result in memory location #2 and #3
000E:   1182    dzsn    $02
000F:   300E    goto    $000E
0010:   1183    dzsn    $03
0011:   300E    goto    $000E
The ret will "jump" to address #0 which is almost same as reset
0012:   007A    ret

The following code is never executed
0008:   1C10    set0io  $10,#0
0009:   380B    call    $000B
000A:   3006    goto    $0006

==> your IC works absolute correct

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 06:57:08 pm
For me it looks like you trash your stack...

Indeed, that seems to be the case. So the newer versions of SDCC start the data segment at 0x02 for some reason.

As mentioned before, better use the newer code.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 02, 2019, 08:11:37 pm

It should be possible to just ship the header files with SDCC (this already happens for some MCS-51 derivatives and some HC08 devices).

The HC08 headers are actually quite interesting. They use bitfield structs to declare individual bits in the I/O ports. I tried to do the same for the PDK14, but got mixed results, see code below.

"PORTA4" is defined as bit4 on PA.

PORTA4^=1  creates functional, but very inefficient code. (11 instructions instead of 3)

PORTA4=1/PORTA4|=1/PORTA4&=~1  creates broken code and SDCC exits with an assembler error.

Code: [Select]
struct __pdk_bits
{
  unsigned int bit0:1;
  unsigned int bit1:1;
  unsigned int bit2:1;
  unsigned int bit3:1;
  unsigned int bit4:1;
  unsigned int bit5:1;
  unsigned int bit6:1;
  unsigned int bit7:1;
};

#define PORTA4 ((struct __pdk_bits *)(&pa))->bit4

#define LEDPIN PA4

unsigned char _sdcc_external_startup(void)
{
clkmd = CLKMD_IHRC_DIV2|CLKMD_ENABLE_IHRC;  // 8 Mhz main clock
return 0; // perform normal initialization
}

void main(void)
{
  pac |= _BV(LEDPIN);     // Use this exact syntax to infer set0/set1
  for (;;) {
  // pa ^= _BV(LEDPIN); // Toggle LED
PORTA4 ^=1;   // works, but creates 11 instructions
delay_ms(500);
PORTA4 = 1;   // creates broken assembler code

  }
}

Code: [Select]
; blinky.c: 38: PORTA4 ^=1;   // works, but creates 11 instructions
mov a, _pa+0
swap a
and a, #0x01
xor a, #0x01
clear p
sr a
mov a, _pa+0
and a, #0xef
t0sn f, c
or a, #0x10
mov _pa+0, a
; blinky.c: 39: delay_ms(500);
mov a, #0xf4
mov _delay_ms_PARM_1+0, a
mov a, #0x01
mov _delay_ms_PARM_1+1, a
call _delay_ms
; blinky.c: 40: PORTA4 = 1;   // creates broken assembler code
mov a, #0x10
or _pa+0, a
goto 00102$
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 02, 2019, 10:26:28 pm
...
Many thanks! After setting the stack address to something else I got the assembly blink working.

The reason why I was considering if my IC's RAM was bad it's because I couldn't get neither the assembly one nor the C one to work, so given this is the first and only PFS154 I've used for testing and has been subject to pretty harsh conditions (such as yesterday when I accidentally got it connected backwards with VCC on GND and vice-versa  |O ), it wouldn't had surprised me.

However the reason the C version wasn't working either wasn't a change in SDCC but an oversight on my side - the library I am using for parsing Intel HEX files gives offsets in bytes, but expects the actual data to be requested in terms of words (https://github.com/socram8888/ArduinoPDKProgrammer/commit/e9779c79b7ce0e3880e679819ae0bc4516c28b26), so I was writing all the time the wrong data at the wrong address. After fixing that I do get the LED to blink just fine.

There's one last blink not working though: the toolkit one. I do not get the LED to turn ON at all, neither I see anything on the scope. I just realized the toolkit one uses PA4, so it's my fault. It's the last time I try to dev stuff past midnight  :palm:

The IHX files from tim_'s repo (https://github.com/cpldcpu/SimPad/tree/b87a4efcbaf8064f70bc0c224c1c8274b46c9646) are these. They have been compiled using the SDCC snapshot of 1st September 2019, and had both been tested to work. I'll leave them there in case somebody wants a quick test hex file:

PFS154Examples/blinkasm (put LED on PA0)
Code: [Select]
:16000000102F8201782F8301012F9101101E2038101C20380630FB
:10004000FF2F820B830B82112330831123307A0020
:00000001FF

PFS154Examples/blinkc (put LED on PA0)
Code: [Select]
:020020007B0063
:1000000000000113042F0128FE2C82011D3812303C
:16002400022F800B1930002F80030012022F022800171530113005
:0200220020308C
:20003A00782F83010002012F9101302F820B752F830B820F0129800B830F6100830B80133F
:20005A00820B8013800E002A2630002F9001302F820B752F830B820F0129800B830F610041
:16007A00830B8013820B8013800E002A3830012F900122307A0082
:00000001FF

Toolchain/examples/pfs1xx_blinky (put LED on PA4)
Code: [Select]
:020020007B0063
:1000000000000113042F0328FE2C82011D3812303A
:16002400022F800B1930002F80030012022F022800171530113005
:0200220020308C
:1C003A00302F83010002111FD001102E9001F42F820B012F830B2B3821307A0059
:20005600820F840B830F850B850F800B840F84128510800E002B42300013800F2829401AF3
:140076002F30322F0129001A3D30001238307A0000007A0097
:00000001FF
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 03, 2019, 07:36:10 am

It should be possible to just ship the header files with SDCC (this already happens for some MCS-51 derivatives and some HC08 devices).

The HC08 headers are actually quite interesting. They use bitfield structs to declare individual bits in the I/O ports. I tried to do the same for the PDK14, but got mixed results, see code below.

"PORTA4" is defined as bit4 on PA.

PORTA4^=1  creates functional, but very inefficient code. (11 instructions instead of 3)

PORTA4=1/PORTA4|=1/PORTA4&=~1  creates broken code and SDCC exits with an assembler error.

However, the pdk (unlike stm8 and hc08) has a separate address space for the I/O to be accessed via __sfr (and __sfr16 for the one 16-bit I/O-register Padauk has).

 So far, I only used and tested access via the __sfr keyword (as in my examples on https://github.com/free-pdk/sdcc-pdk-code-examples). I don't know if the struct / bit-field approach canbe combined with __sfr.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 03, 2019, 09:50:00 am
Quote
I mean C1 on your programmer board (I think it is for the high voltage output). Also Y1 (the oscillator) was missing in the picture from you. Did you change the firmware to use the HSI48 clock source instead of the external OSC?

The cap you added on the PADAUK MCU is contra productive since it might require different timing for VPP / VDD phase of programming (remove it for testing).

JS
I have soldered a 47uF 1206 ceramic cap for the 15V output already. Also I have not soldered a 8MHz crystal yet, because I do not have stock yet, Since the programmer can talk to PC, it means it can generate the USB 48MHz clock internally, does this may be a problem?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ebclr on September 03, 2019, 12:12:33 pm
I was interested in build this programmer,  but I realize that is a nonsense use this CPU, while I have a 15 cents Cpu that is 8051 compatible, as USB , and don't need any programer just plug to USB and is all set.

12 cents will not cover all the trouble, it's easy to cut development cost and pay 12 cents more on the CPU CH551G is just 15 cents

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 03, 2019, 12:54:03 pm
That's like 500% more expensive  ;)

Besides, it's not only more expensive, but it's also way way more power hungry, using 11mA peak vs 300uA peak, and 20uA vs 500nA in sleep. If you're gonna run on batteries, which is my purpose for these micros, it's a no-go.

A MDT micro would be a suitable replacement, but a power-hungry, AVR-priced USB thing? Geez no.

Besides, at least for me, this is just a matter of trying exotic, chinese stuff rather than getting anything serious working on the platform. It's like that evening you spend coding in Brainfuck just for fun, except on the hardware side.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 03, 2019, 05:42:25 pm
So far, I only used and tested access via the __sfr keyword (as in my examples on https://github.com/free-pdk/sdcc-pdk-code-examples). I don't know if the struct / bit-field approach canbe combined with __sfr.

Well, lets look at the positive side. Some of it already works :)

I looked at gen.c and it is quite clear why it behaves like it currently does. Implementing bitfield for I/O could actually be easier than for memory, since there are dedicated instructions for bit moving like "SWAPC".

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 03, 2019, 05:43:45 pm
Besides, at least for me, this is just a matter of trying exotic, chinese stuff rather than getting anything serious working on the platform. It's like that evening you spend coding in Brainfuck just for fun, except on the hardware side.

So, how about Brainfuck on a $0.03 Padauk MCU?

Edit:
Looks very doable. The brainfuck program will reside in the flash. And one should precalc the target addresses, so most of the RAM can be used for the array.

Code: [Select]
/* simple brainfuck interpreter */
/* 20 April 2006 */
/* Daniel B. Cristofani */
/* http://www.brainfuck.org/ */

#include <stdio.h>
#include <stdlib.h>
#define ARRAYSIZE 65536
#define MAXCODESIZE 65536

//For simplicity, we'll use statically allocated arrays with matching indices.
int stack[MAXCODESIZE], stackp; //to store locations of still-unmatched '['s.
char code[MAXCODESIZE]; int codep, codelength; //copy of the program we'll read into memory.
short int array[ARRAYSIZE], memp; //the memory used by the brainfuck program.
int targets[MAXCODESIZE]; //to save matching '[' for each ']' and vice versa.
int c;
FILE *prog;

int main(int argc, char **argv){
    if (argc > 2) fprintf(stderr, "Too many arguments.\n"), exit(1);
    if (argc < 2) fprintf(stderr, "I need a program filename.\n"), exit(1);
    if(!(prog = fopen(argv[1], "r"))) fprintf(stderr,"Can't open the file %s.\n", argv[1]),exit(1);
    codelength = fread(code, 1, MAXCODESIZE, prog);
    fclose(prog);
    for(codep=0; codep<codelength; codep++){
        if (code[codep]=='[') stack[stackp++]=codep;//put each '[' on the stack
        if (code[codep]==']'){ //If we meet a ']',
            if(stackp==0){ //and there is no '[' left on the stack, it's an error.
                fprintf(stderr,"Unmatched ']' at byte %d.", codep), exit(1);
            } else {
                --stackp; //if there is one, we take the matching '[' from the stack top,
                targets[codep]=stack[stackp]; //save it as the match for the current ']',
                targets[stack[stackp]]=codep; //and save the current ']' as the match for it.
            }
        }
    }
    if(stackp>0){ //Any unmatched '['s still left on the stack are an error too.
        fprintf(stderr,"Unmatched '[' at byte %d.", stack[--stackp]), exit(1);
    }
    for(codep=0;codep<codelength;codep++){//Everything is okay; we start executing the program.
         switch(code[codep]){
            case '+': array[memp]++; break;
            case '-': array[memp]--; break;
            case '<': memp--; break;
            case '>': memp++; break;
            case ',': if((c=getchar())!=EOF) array[memp]=c=='\n'?10:c; break;
            case '.': putchar(array[memp]==10?'\n':array[memp]); break;
            case '[': if(!array[memp]) codep=targets[codep]; break;
            case ']': if(array[memp]) codep=targets[codep]; break;
        }
    }
    exit(0);
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 04, 2019, 01:49:41 pm
So I have been still working with the PFS154. I have just sent the PCBs for the Arduino-based programmer to JLCPCB, and we'll see how good they work. At least on my protoboard it's been working fine, so that one better do too  :D

The project on EasyEDA is here: https://easyeda.com/socram8888/arduino-pfs-programmer

Regarding the chip itself, yesterday night I got working my first project from scratch for the PFS154. It's meant to replace the microcontroller inside a particular model of bike horns sold on Aliexpress, which generates a siren similar to ambulances. My solution generates a different tone, more similar to a horn and thus more suitable for a bike or a Xiaomi scooter.

It's using timer features, deep sleep modes, clock switching and some other features, so if you want to try something more advanced, here it is: https://github.com/socram8888/PFS154Horn

It generates a tone in PA3 whenever the button on PA0 is pressed (connected to ground)

PS: I do wonder if the original horn is using a PMC150 for the siren sound effect, since it's also a number-less part in SOIC8 whose epoxy case looks a lot like that of my PFS154.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 04, 2019, 03:20:20 pm
Hi,

today some PCBs arrived.  :)

I have made a PMS150C-8/PFS154-8/PFS173-8 audio player (PCM, 8 bit, 32kHz) reading from SPI flash or SD card. Sound quality is very nice.
Total cost for MCU/Flash/Amplifier/Speaker is less than 60 cent  :) I think this is the cheapest option to play any high quality sound.
My particular use case is to play the Apple-Startup sound on my hackintosh whenever it is power cycled 8)

I will cleanup some things and upload the complete project as an example soon. It contains a nice set of features like SPI, PWM, Timer Interrupts and is still very small.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on September 05, 2019, 05:06:05 am
I'm trying to buy the parts from the BOM file in the github and it seems it's for LCSC, but when I load the CSV into LCSC using their BOM tool it's just a mess.
Anyone know why?
It is because it's semicolon delimited instead of coma delimited?
Thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on September 05, 2019, 05:13:57 am
I'm trying to buy the parts from the BOM file in the github and it seems it's for LCSC, but when I load the CSV into LCSC using their BOM tool it's just a mess.
Anyone know why?
It is because it's semicolon delimited instead of coma delimited?
Thanks.

I downloaded the LCSC BOm template and manually copied everything over and it's still a mess when I import it into LCSC  |O

Turns out there is a bug in the LCSC BOM. It re-loads the previous (incorrect) file even when you try and upload a new one. You have to restart the web page.

XLS BOM attached in LCSC format
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 05, 2019, 12:11:04 pm
I downloaded the LCSC BOm template and manually copied everything over and it's still a mess when I import it into LCSC  |O

Turns out there is a bug in the LCSC BOM. It re-loads the previous (incorrect) file even when you try and upload a new one. You have to restart the web page.

XLS BOM attached in LCSC format

Hi,

Thanks for bringing this up. Looks like export/import from EasyEDA / LCSC is language dependent (my language uses semicolons in CSVs, so maybe that's why it was working for me).

I added your excel file to the github repository. This should be always working now.


For simplicity I suggest that you order a SOP socket (keep an eye on the spacing of the pin headers, some are narrow, some are wide).
This one should work: https://www.aliexpress.com/item/32890300159.html (https://www.aliexpress.com/item/32890300159.html)

This can be used with all SOP versions of PMC150C / PFS154 / PFS173 / ... and fits directly on top of the programmer.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 05, 2019, 01:10:45 pm
JS I made progress! I have soldered a 8MHz crystal to the board and now it can Erase the part ok, But when I read it, it says "Could not read data from programmer"
 |O |O

(https://img.techpowerup.org/190905/untitled.png)
what should I do?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 05, 2019, 05:27:13 pm
JS I made progress! I have soldered a 8MHz crystal to the board and now it can Erase the part ok, But when I read it, it says "Could not read data from programmer"

Hi,

It already looks very good!
The read command already executed correctly ("Reading IC... done."). This means the programmer was able to read out the IC into its internal buffer.

The error you get is from USB communication only. The command to get the data from programmer back to your PC failed for some reason (it just sends more data then the previous commands).

Did USB disconnect in this moment (observe in device manager if device disappears when you do the read).
If so, I would suggest to inspect the 8MHz crystal soldering and the 2 small caps next to the crystal. USB is very picky with the 48MHz bus clock speed and possible drifts.

Another possibility could be a bad USB cable / bad USB hub / ... Easiest way to find out is to connect the programmer directly to the computer and / or try it on another computer. Then you know it is either the programmer or something else.

EDIT: A friend of mine reported the same problem on Windows 10... I will have a look later. Maybe your programmer works correct already.


You are almost there.

Update: I was able to reproduce the problem and added a fix for Windows. New development version (and release) will not give this strange error anymore:

https://github.com/free-pdk/easy-pdk-programmer-software/releases

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 07, 2019, 05:51:58 am
Dear JS, Thanks for your help and support, big thumbs up :-+
Now it's working, my Design did not have any problem, it was just not soldering the crystal, so you can now add my Altium files to the repo if you want ;)

Also Now is the time to do some programming...

how to get started with SDCC for PFS173, I see your examples and they are for PFS154, is there something that I should change?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 07, 2019, 06:14:32 am
how to get started with SDCC for PFS173, I see your examples and they are for PFS154, is there something that I should change?

Despite having -pfs154 in the name, both hello-pfs154 and count-pfs154 are written to work on both: When using sdcc -mpdk14 they get compiled for PFS154, when using sdcc -mpdk15 they get compiled for PFS173.

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 07, 2019, 07:51:37 am
Thanks, I have done two project successfuly, JS I think I have found another bug in the PC software

I have modified the Hello example to output the UART on the PA.7 port, so after starting easypdkprog, it should capture the UART data, it can not get the UART data for now, But I have connected an external UART Bridge(FT230x) to it and it's putting data on the line,
(https://img.techpowerup.org/190907/untitled.jpg)

here is the Modified code for PFS173.

Code: [Select]
// "Hello, world!" for the Padauk PFS154, to be compiled with SDCC.
// Repeatedly outputs the string "Hello, World!" at 9600 baud on pin 0 of Port A.
// Written by Philipp Klaus Krause in 2019.
// Source code under CC0 1.0.

// Output on PA0 at 1200 baud.

#include <stdbool.h>
#include <stdio.h>

volatile unsigned char sendcounter;
volatile unsigned int senddata;
volatile bool sending;

//PFS173 SFR's
__sfr __at(0x00) flag;
__sfr __at(0x02) sp;
__sfr __at(0x03) clkmd;
__sfr __at(0x04) inten;
__sfr __at(0x05) intrq;
__sfr __at(0x06) t16m;
__sfr __at(0x0a) eoscr;
__sfr __at(0x0b) ihrcr;
__sfr __at(0x0c) integs;
__sfr __at(0x0d) padier;
__sfr __at(0x0e) pbdier;
__sfr __at(0x0f) pcdier;
__sfr __at(0x10) pa;
__sfr __at(0x11) pac;
__sfr __at(0x12) paph;
__sfr __at(0x13) pb;
__sfr __at(0x14) pbc;
__sfr __at(0x15) pbph;
__sfr __at(0x16) pc;
__sfr __at(0x17) pcc;
__sfr __at(0x18) pcph;
__sfr __at(0x19) pbpl;
__sfr __at(0x1a) pcpl;
__sfr __at(0x20) adcc;
__sfr __at(0x21) adcm;
__sfr __at(0x22) adcr;
__sfr __at(0x24) adcrgc;
__sfr __at(0x26) misc;
__sfr __at(0x2b) gpcc;
__sfr __at(0x2c) gpcs;
__sfr __at(0x30) tm2c;
__sfr __at(0x31) tm2ct;
__sfr __at(0x32) tm2s;
__sfr __at(0x33) tm2b;
__sfr __at(0x34) tm3c;
__sfr __at(0x35) tm3ct;
__sfr __at(0x36) tm3s;
__sfr __at(0x37) tm3b;
__sfr __at(0x40) pwmg0c;
__sfr __at(0x41) pwmgclk;
__sfr __at(0x42) pwmg0dth;
__sfr __at(0x43) pwmg0dtl;
__sfr __at(0x44) pwmgcubh;
__sfr __at(0x45) pwmgcubl;
__sfr __at(0x46) pwmg1c;
__sfr __at(0x48) pwmg1dth;
__sfr __at(0x49) pwmg1dtl;
__sfr __at(0x4c) pwmg2c;
__sfr __at(0x4e) pwmg2dth;
__sfr __at(0x4f) pwmg2dtl;

void send_bit(void) __interrupt(0)
{
// Reset interrupt request, proceed only if we had a timer interrupt.
if(!(intrq & 0x40))
{
intrq = 0x00;
return;
}
intrq = 0x00;

if(!sending)
return;

if(senddata & 1)
pa = 0x80;
else
pa = 0x00;

senddata >>= 1;

if(!--sendcounter)
{
sending = false;

inten &= ~0x40;
}
}

int putchar(int c)
{
while(sending);

senddata = (c << 1) | 0x200;

sendcounter = 10;

tm2ct = 0;

sending = true;

inten |= 0x40;

return (c);
}

unsigned char _sdcc_external_startup(void)
{
#ifdef __SDCC_pdk15
ihrcr = *((const unsigned char*)(0x8bed)); // Use PFS173 factory calibration value for IHRC at 16 Mhz.
#else
ihrcr = *((const unsigned char*)(0x87ed)); // Use PFS154 factory calibration value for IHRC at 16 Mhz.
#endif

clkmd = 0x34; // Use IHRC / 2 = 8 Mhz for system clock, disable watchdog.
clkmd = 0x30; // Disable ILRC

return 0; // perform normal initialization
}

void main(void)
{
// Set timer 2 for interrupt for 1200 baud.
tm2c = 0x10; // Use CLK (8 Mhz)
tm2s = 0x06; // Divide by 6 + 1 ~> 1142857 Hz
tm2b = 118;  // Divide by 118 + 1 ~> 9604 Hz
inten = 0x40;
__asm
engint
__endasm;

pac = 0x81;

for(;;)
{
printf("ASiDesigner!\r\n");
for(unsigned long int i = 0; i < 150000; i++); // Wait approx. 3s.
}
}




Also I have another question, is it possible to run the device @ 16MHz, I have changed the clkmd =0x54; and it's certainly running @ 8MHz.
(https://img.techpowerup.org/190907/untitled1.jpg)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 07, 2019, 08:10:25 am
Does the printf accept additional arguments? :-\
Code: [Select]
printf("ASiDesigner! %d\r\n",k);
k++;

if Not,I suppose we write something like this library for AVR (General purpose numeral output module)  form http://elm-chan.org/docs/avrlib/xitoa.zip (http://elm-chan.org/docs/avrlib/xitoa.zip)
Unfortunately it's in AVR asm, But it should be some way of porting it to PADAUK.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 07, 2019, 11:06:45 am
I have modified the Hello example to output the UART on the PA.7 port, so after starting easypdkprog, it should capture the UART data, it can not get the UART data for now, But I have connected an external UART Bridge(FT230x) to it and it's putting data on the line,
There is no "BUG" with easypdkprog. EasyPDK programmer features AUTO-BAUD-DETECTION which requires to send 0x55 as first character followed by at lest 4 extra stop bits (or a small delay) to internally apply the baud rate.
It is reported to work fine with baud rates up to 1.5 Mbit.

I'm working on a clean "Hello World!" example project, which will be included in easypdkprog release.

Also I have another question, is it possible to run the device @ 16MHz, I have changed the clkmd =0x54; and it's certainly running @ 8MHz.
How did you measure the internal clock speed? Serial port implementation in the sdcc-example program which you used is based on IHRC directly, not on SYSCLK, This means baud rate will not change when you change SYSCLK.

Does the printf accept additional arguments? :-\
Yes it does. Most likely the SDCC library is not compiled as "small" so the full printf (including support for width adjustments, leading spaces / zeros / floats / ...) implementation simply does not fit in our ultra ultra small RAM.


JS

EDIT: It is included in the Release now: https://github.com/free-pdk/easy-pdk-programmer-software/releases/latest
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 07, 2019, 06:43:18 pm
Also I have another question, is it possible to run the device @ 16MHz, I have changed the clkmd =0x54; and it's certainly running @ 8MHz.

I don't know. I've asked Padauk, but didn't get a reply yet.
For the PFS173, PMS133 and PMS134, the datasheets are contradictionary on that question. Section 6.3 vs. sections 5.4.2 and 5.4.5.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 08, 2019, 05:15:41 am
Thanks JS :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 08, 2019, 10:56:47 am
Is there a way to tell how much flash and ram is used with SDCC? ^-^
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 08, 2019, 11:33:53 am
Is there a way to tell how much flash and ram is used with SDCC? ^-^

Flash is easy. Have a look at the .map file.
For RAM, in general, you'd have to solve the halting problem (the data from the .map file does not include RAM used for the stack).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 09, 2019, 06:40:28 am
Thanks,Is there a way to add it to the command prompt? using make to tell the flash usage?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 09, 2019, 06:59:38 am
Guys I have some Idea, is it possible to add easypdkprog into the SDCC tool's, I mean adding the executable's to the distribution,

Something like winAVR for AVR. they had put AVRDUDE in it.

Then we can make a generic make file with the programming command too, also If there is some way of adding the code generated examples for PADAUK IDE for USART send,receive, I2C, SPI, PS2 and ADC it would be very nice too. I think the AVR and winavr was a smart choice at that time and place,(you could easily change the CPU name and FPCU in make file) and also PADAUK are very similar to lower end AVR's, still cheaper tough >:D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 09, 2019, 07:06:21 am
Thanks,Is there a way to add it to the command prompt? using make to tell the flash usage?

If you don't use any custom segments, the const segment is last in Flash. So you could parse the line, e.g.
Code: [Select]
Area                                    Addr        Size        Decimal Bytes (Attributes)
--------------------------------        ----        ----        ------- ----- ------------
CONST                               0000106E    00000B16 =        2838. bytes (REL,CON)
with grep to get the start and size, then add them (e.g. using bc with ibase=16), then divide by 2 to get the size in words.

If you are just worried about exceeding the available Flash: The Linker will warn you about that (if you have a device that has the maximum Flash that the architecture supports).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 09, 2019, 09:28:08 am
Thanks, It's always beneficial to have some info, Today I'm working on embOS, such a great OS for Cortex M devices, though I have used a lot FreeRTOS and RTX, but now I prefer embOS simply because it would get much more info from inside the internal workings!

If we could have something like this, it would be very helpful


Quote
Program Size: Code=15080 RO-data=464 RW-data=284 ZI-data=4704 
>:D

can we have an OS on PAUDUK, something like this

http://www.femtoos.org/ (http://www.femtoos.org/)


or Am I dreaming ::) ::) ::)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 09, 2019, 09:37:30 am
can we have an OS on PAUDUK, something like this

http://www.femtoos.org/ (http://www.femtoos.org/)


or Am I dreaming ::) ::) ::)

Maybe, but it probably would work only on the bigger devices. Maybe try porting a more leightweight OS, such as Atomthreads first?
It probably won't we worth using an OS on such a small device though.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 09, 2019, 10:55:01 pm
Then we can make a generic make file with the programming command too, also If there is some way of adding the code generated examples for PADAUK IDE for USART send,receive, I2C, SPI, PS2 and ADC it would be very nice too. I think the AVR and winavr was a smart choice at that time and place,(you could easily change the CPU name and FPCU in make file) and also PADAUK are very similar to lower end AVR's, still cheaper tough >:D

I started putting some things together. It will automatically compile&program and also output program length:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain (https://github.com/cpldcpu/SimPad/tree/master/Toolchain)

Still very much work in progress. Next step would be a smaller printf function. And we also need agreement on SFR names... My current favourite would be to use all capitals, like it is done for all other 8bit MCUs.

Regarding a multitaskting OS: I believe that is quite in contradiction to the "FPPA" paradigm. The idea of the Padauk MCUs is to do multithreading with deterministic timing in hardware. That is much more valuable than preemptive multitasking in software and requires little software overhead. Software based preemtive multitasking will not allow you to implement virtual periphery, as it is possible with the FPPA approach.

edit: Of course you could use one FPPA with a multitaksing OS and use other FPPAs for virtual periphery. Things are getting a tad bit complex then.

For those that are a bit more into computer architecture, you can find an introduction to XMOS below. This is based on similar ideas as the padauk FPPA.

https://www.hotchips.org/wp-content/uploads/hc_archives/hc23/HC23.18.4-DSP/HC23.18.410-XMOS-XS1-May_Xmos.pdf (https://www.hotchips.org/wp-content/uploads/hc_archives/hc23/HC23.18.4-DSP/HC23.18.410-XMOS-XS1-May_Xmos.pdf)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 09, 2019, 11:00:15 pm
Also I have another question, is it possible to run the device @ 16MHz, I have changed the clkmd =0x54; and it's certainly running @ 8MHz.

I don't know. I've asked Padauk, but didn't get a reply yet.
For the PFS173, PMS133 and PMS134, the datasheets are contradictionary on that question. Section 6.3 vs. sections 5.4.2 and 5.4.5.

Please let us know their response. I am getting the feeling that the PDK architecture is indeed a 2 cycle architecture. I was also fooled by the clock options initially. But then, there are some instruction that are very hard to efficiently implement in a 1 cycle architecture. For example the memory RMW-instructions (INC, many others). These would require a two port memory or would be very wasteful in ressources (f.e. double edge memory access).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 10, 2019, 05:36:38 am
Regarding a multitaskting OS: I believe that is quite in contradiction to the "FPPA" paradigm. The idea of the Padauk MCUs is to do multithreading with deterministic timing in hardware. That is much more valuable than preemptive multitasking in software and requires little software overhead. Software based preemtive multitasking will not allow you to implement virtual periphery, as it is possible with the FPPA approach.

edit: Of course you could use one FPPA with a multitaksing OS and use other FPPAs for virtual periphery. Things are getting a tad bit complex then.

For those that are a bit more into computer architecture, you can find an introduction to XMOS below. This is based on similar ideas as the padauk FPPA.

https://www.hotchips.org/wp-content/uploads/hc_archives/hc23/HC23.18.4-DSP/HC23.18.410-XMOS-XS1-May_Xmos.pdf (https://www.hotchips.org/wp-content/uploads/hc_archives/hc23/HC23.18.4-DSP/HC23.18.410-XMOS-XS1-May_Xmos.pdf)

Their current FPPA paradigm is not very compatible with C. It looks like they designed a non-parallel instruction set, and then just made some parallel devices.
SDCC currently does not support multiple FPPA.

For efficient parallelism for the Padauk µC, we'd need:
* Stack-pointer-relative addressing and better stack handling (I'm currently running some experiments - when you compile code with --stack-auto for the current architecure, code size triples)
* Synchronization. We would need at least a compare-and-swap instruction, and an xch withindirect addressing mode. Preferably also an idxadd variant of add M, a.

I believe I can add support for multiple FPPA to SDCC. But the generated code will be big and slow. For practical purposes, running a multitasking OS on a single FPPA would be more efficient.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 10, 2019, 06:49:36 am

Their current FPPA paradigm is not very compatible with C. It looks like they designed a non-parallel instruction set, and then just made some parallel devices.
SDCC currently does not support multiple FPPA.

For efficient parallelism for the Padauk µC, we'd need:
* Stack-pointer-relative addressing and better stack handling (I'm currently running some experiments - when you compile code with --stack-auto for the current architecure, code size triples)
* Synchronization. We would need at least a compare-and-swap instruction, and an xch withindirect addressing mode. Preferably also an idxadd variant of add M, a.

I believe I can add support for multiple FPPA to SDCC. But the generated code will be big and slow. For practical purposes, running a multitasking OS on a single FPPA would be more efficient.

I don't think true c-compatible paralellism was their ultimate goal. (They don't even provide a C-compiler...). Obviously that would have added a lot of additional complexity, as you point out.

The idea is probably to have specific tasks assigned to specific threads. For example one thread runs the SPI peripheral, a second one runs a control loop, while the main thread mostly sleeps and does housekeeping/reconfiguration. Each of these would reside in their own memory space with dedicated ressources and would use minimal inter-thread communication via pipes. This would keep synchronization overhead down a lot.

For SDCC, the main challenge would be to allow multiple main function to initialize each FPPA. Maybe that could be dont similar to interrupts? It would be up to the user to ensure that variables are not reused between different threads.

Of course, something needs to be done with the p-register. A very rigid approach would be to clearly assign each function to only one FPPA.

A more pragmatic approach, for now, would be to have C-code always stay on FPPA0 and use assembler for the others...

Regarding preemtive multitasking: Of course this would free up some of the synchronization headache, but then the usefulness would be quite limited compared to using multiple hardware threads.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 13, 2019, 05:53:20 pm
Brainfuck, now also on Padauk:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain/examples/pfs1xx_brainfuck
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on September 14, 2019, 07:19:23 pm
https://www.youtube.com/watch?v=5jw5D0F008c (https://www.youtube.com/watch?v=5jw5D0F008c)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 14, 2019, 11:38:00 pm
...

That's quite interesting. Is that your video?

So the die size  of the PMS150 seems to be ~0.3mm². That is really small. For example an ATtiny4, which is Microchips lowest cost product, is ~1.25mm² (https://zeptobars.com/en/read/atmel-tiny4-attiny4-microcontroller (https://zeptobars.com/en/read/atmel-tiny4-attiny4-microcontroller)). The ATtiny4 most likely uses a much older process, though.

The size of the OTP area of ther PMS150C is roughly 0.0433 mm², assuming that the picture shows the full area of the die. This is very close to the size of the 1k14 macro of Ememory's "Neobit" OTP memory: http://www.ememory.com.tw/html/products_green_neobit.php (http://www.ememory.com.tw/html/products_green_neobit.php)  A coincidence? Maybe not, there are not too many independent vendors of suitable memory IP around...

This memory technology is specifically designed to be manufacturable in low complexity (low mask count) foundry processes. 0.3 mm² of silicon in a 15 mask count 0.18µm process costs less than 0.01 USD in volume*. The challenge would be to get the product developed, packaged, tested, yielded and distributed for fractions of a cent. If that is solved, then a 3 cent microcontroller does not look too outlandish.

---
*Average wafer price for 200mm on 0.18µm across the industry is $625: https://anysilicon.com/major-pure-play-foundries-revenue-per-wafer-2017-2018/ (https://anysilicon.com/major-pure-play-foundries-revenue-per-wafer-2017-2018/)

The usable area of a 200mm Wafer is approximately 30000mm², so there are ~100000 PMS150C per wafer. This would correspond to $0.006 per die.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: oPossum on September 14, 2019, 11:48:44 pm
That's quite interesting. Is that your video?

No, not my video.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 16, 2019, 08:23:45 am
I don't think true c-compatible paralellism was their ultimate goal. (They don't even provide a C-compiler...). Obviously that would have added a lot of additional complexity, as you point out.
Still, on such a "multicore" µC, you want efficient communication between multiple cores and interrupt handlers, which means efficient lockless atomics, which means a compare-and-swap instruction, preferably with indirect addressing mode.
Quote
The idea is probably to have specific tasks assigned to specific threads. For example one thread runs the SPI peripheral, a second one runs a control loop, while the main thread mostly sleeps and does housekeeping/reconfiguration. Each of these would reside in their own memory space with dedicated ressources and would use minimal inter-thread communication via pipes. This would keep synchronization overhead down a lot.

For SDCC, the main challenge would be to allow multiple main function to initialize each FPPA. Maybe that could be dont similar to interrupts? It would be up to the user to ensure that variables are not reused between different threads.

Of course, something needs to be done with the p-register. A very rigid approach would be to clearly assign each function to only one FPPA.

A more pragmatic approach, for now, would be to have C-code always stay on FPPA0 and use assembler for the others...

Regarding preemtive multitasking: Of course this would free up some of the synchronization headache, but then the usefulness would be quite limited compared to using multiple hardware threads.

SDCC is a C compiler, and will aim to comply with the C standard. Where that can't be done efficiently, we still need to be able to comply, but offers alternatives. E.g. when compiling for Padauk, functions are currently not reentrant by default (but reentrancy can be enabled for individual functions using __reentrant, or for the whole program using --stack-auto; it about triples code size though).

For multiple FPPA, my idea would be:

By default make the code work on any FPPA. That means a lock around any use of p. And no longer using p to pass return values (thus 16-bit return values would have to be passed on the stack, like we currently do for return values > 16 bit). Inefficient, but avoids nasty surprises.

Then provide a way for the user to specify that a function is to be used on a specific FPPA only, e.g. something like
Code: [Select]
[[sdcc::fppa(3)]] void f(int)
{

}
An FPPA3-specific p3 would be used instead of p when generating code for f.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 19, 2019, 05:45:28 am
Still, on such a "multicore" µC, you want efficient communication between multiple cores and interrupt handlers, which means efficient lockless atomics, which means a compare-and-swap instruction, preferably with indirect addressing mode.
Well, this simply is not a universial multicore architecture. It is to be used within very narrow constraints. For example, if threads are used to emulate virtual periphery, it should be sufficient to work with very simple messaging schemes instead of comprehensive synchronisation. In most cases there will be a clear producer/consumer relationship and it will not be necessary to synchronize two or more threads with the same priority. There is also no real benefit from avoiding active waiting.

Btw, it should also be possible to use the atomic xch instruction? This is effectively like a CAS that can only compare to a single value.

Code: [Select]
  mov a,#1
loop:
   xch a,lock
   ceqsn a,#0
   goto loop:

[...critical block...]

  clear lock




Quote

SDCC is a C compiler, and will aim to comply with the C standard. Where that can't be done efficiently, we still need to be able to comply, but offers alternatives. E.g. when compiling for Padauk, functions are currently not reentrant by default (but reentrancy can be enabled for individual functions using __reentrant, or for the whole program using --stack-auto; it about triples code size though).

For multiple FPPA, my idea would be:

By default make the code work on any FPPA. That means a lock around any use of p. And no longer using p to pass return values (thus 16-bit return values would have to be passed on the stack, like we currently do for return values > 16 bit). Inefficient, but avoids nasty surprises.

Then provide a way for the user to specify that a function is to be used on a specific FPPA only, e.g. something like
Code: [Select]
[[sdcc::fppa(3)]] void f(int)
{

}
An FPPA3-specific p3 would be used instead of p when generating code for f.

This sounds like a good plan. Now we only need the flash variants with more than 1 FPPA to be released. :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 19, 2019, 06:46:12 pm
Btw, it should also be possible to use the atomic xch instruction? This is effectively like a CAS that can only compare to a single value.


No. xch is just a plain swap, no compare there. It still can be used to implement spinlocks, which are useful as building blocks for more advanced functionality (though for spinlocks, there is a sightly more efficient alternative using srl instead). If xch had an indirect adressing mode, it could also be used to implement the atomic_flag type (but it doesn't).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 21, 2019, 05:32:27 pm
FYI - some updates on my attempt on a toolchain:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain

I implemented size-optimized softuart functions to be used as a serial debugger, including TX, string and number printing. They are less than 100 instructions in total and therefore should not interfere even with larger programs.

https://github.com/cpldcpu/SimPad/tree/master/Toolchain/examples/uartsend

Maybe I will integrate this into a minimized printf some time later. The printf provided in the standard library does not fit into the PFS154 code space right now, unless you force it to infer a "puts" by printing a string terminated with \n. I found this highly confusing.

Right now, the implementation has to be integrated by #including the c-code. I am not completely happy with that, but found no simpler way to avoid always including the binary. It seems that the linker for the PDK14 architecture will also link unused binaries?

Apart from that, the includes now support upper case SFR names as defines. This allows intellisense in VSCODE to work to at least some extend.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 22, 2019, 06:33:33 am
Thumbs up :-+ adding RX to it would be nice too ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 22, 2019, 06:54:06 am
Thumbs up :-+ adding RX to it would be nice too ;)

Well, there is just no straightforward way of doing that.

Option 1): Use no interrupt, RX routine has to wait until it receives a character.
Option 2): Use a pin change interrupt to detect RX, receive in interrupt handler.
Option 3): Thread on a separate FPPA

Option 1) means that you have to actively wait for RX in your mainloop. High risk of losing data, basically no time to do anythign else. Option 2) should be more stable. However it would occupy the one and only interrupt of your device. That's a bit intrusive for something that is to be used for debugging. Option 3) would be the way it is intended. However right now we don't have flash devices with 2 or more FPPA.

Well, I may work my way through all of these options at one point.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 22, 2019, 08:30:43 am
I think option 2 is the best for single cores!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 22, 2019, 09:35:33 am
Thumbs up :-+ adding RX to it would be nice too ;)

I implemented UART RX/TX based on timer interrupt some time ago. I cleaned up and added the source to the examples folder in development branch:

https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples

Apart from that, the includes now support upper case SFR names as defines. This allows intellisense in VSCODE to work to at least some extend.

This is a a good reason to switch to all upper case in general for all IO registers. I will change my includes as well.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 22, 2019, 05:08:43 pm
Hi,

I got hold of 2 more PADAUK MCUs and added (partial) support for them in development branch:

PMS15A:
- this is just a marketing derivat of the good old PMS150C. It has exact same chip inside and reports as PMS150C.
- you can see that they are same in PADAUK IDE include folder: Compared to PMS150C, the include for PMS15A just has one suspicious extra line: ".Assembly User_Size 200h" which limits IDE code size...

MCU390: http://www.zhienchina.com/products/1556.html (http://www.zhienchina.com/products/1556.html)
- in older PADAUK IDE there was an include for MCU390 (now missing)
- on the "manufacturer" web site you can find interesting things like how to use the PADAUK IDE with libraries and the ICE with trace / uart / stimulus (one big archive containing everything): http://www.zhienchina.com/Upfiles/down/MCU39X%E8%A7%A6%E6%91%B8%E8%8A%AF%E7%89%87%E5%BC%80%E5%8F%91%E5%8C%85.rar (http://www.zhienchina.com/Upfiles/down/MCU39X%E8%A7%A6%E6%91%B8%E8%8A%AF%E7%89%87%E5%BC%80%E5%8F%91%E5%8C%85.rar)

:-)

JS
Title: Is IHRC and BGTR calibration automatically read from flash?
Post by: tim_ on September 22, 2019, 10:17:27 pm
I have been experimenting with the IHRC and BGTR-calibration. As JS notedin an older post, there are calibration values stores on the flash in the PFS154/163 in two read-only memory addresses.

It appears to me, that these are automatically loaded into the respective registers. The dump below shows the initial value of IHRCR and BGTR and it is exactly the same as the value stored on the flash. The value is also the same that EASYPDKPROG ends up with during calibration. It appears that no calibration is needed on the flash types, unless you want to adjust to a different voltage?

Is this confirmed anywhere?

I also noted that IHRCR is readable, although it is marked as write only in the official .INC file.

Also strange: The low frequency oscillator calibration register (ILRCR) has the same initial value as the IHRCR. There is no corresponding value in the flash.

Code: [Select]
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 0282 025A 1FFE
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
IHRCAL: 82
IHRCRNOW: 82
ILRCRNOW: 82
BGTCAL: 5A
BGTRNOW: 5A
from include file:
Code: [Select]
IHRCR IO_WO 0x0B
ILRCR IO_WO 0x39 (-) // [7:4]
BGTR IO_RW 0x1A (0x2C) // [7:3]
Title: Re: Is IHRC and BGTR calibration automatically read from flash?
Post by: js_12345678_55AA on September 22, 2019, 11:40:56 pm
I have been experimenting with the IHRC and BGTR-calibration. As JS notedin an older post, there are calibration values stores on the flash in the PFS154/163 in two read-only memory addresses.

It appears to me, that these are automatically loaded into the respective registers. The dump below shows the initial value of IHRCR and BGTR and it is exactly the same as the value stored on the flash. The value is also the same that EASYPDKPROG ends up with during calibration. It appears that no calibration is needed on the flash types, unless you want to adjust to a different voltage?

Is this confirmed anywhere?

I also noted that IHRCR is readable, although it is marked as write only in the official .INC file.

Also strange: The low frequency oscillator calibration register (ILRCR) has the same initial value as the IHRCR. There is no corresponding value in the flash.

Code: [Select]
07E0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 0282 025A 1FFE
07F0: 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF 3FFF
IHRCAL: 82
IHRCRNOW: 82
ILRCRNOW: 82
BGTCAL: 5A
BGTRNOW: 5A
from include file:
Code: [Select]
IHRCR IO_WO 0x0B
ILRCR IO_WO 0x39 (-) // [7:4]
BGTR IO_RW 0x1A (0x2C) // [7:3]

The factory values are encoded as "RET i" where i is the calibration value.

My observations showed that those values are not "auto loaded". However if you use Padauk IDE they always insert calls for factory BGTR tuning in startup code and maybe with some settings also for IHRCR.

IHRCR / ILRCR / BGTR are WRITE-ONLY registers. So not sure how / why it was possible for you to read them back? ... interesting?

Factory calibrated IHRC value is fully understood and documented (calibration value is for 5V / 16MHz):

The following macros can be used in SDCC:

#define PFS154_USE_FACTORY_IHRCR_16MHZ() { _ihrcr = *((const unsigned char*)(0x87ed)); }

#define PFS173_USE_FACTORY_IHRCR_16MHZ() { _ihrcr = *((const unsigned char*)(0x8bed)); }


BGTR is bandgap tuning. You need this when you want to use the comparator or ADC. It will tune the internal band gap to 1.2V (which can be used as reference for internal comparator or ADC)

I prepared some tests and will implement auto tuning for it in next release of programmer.

There are also factory calibrated values:

#define PFS154_USE_FACTORY_BGTR() { _bgtr = *((const unsigned char*)(0x87ee)); }

#define PFS173_USE_FACTORY_BGTR() { _bgtr = *((const unsigned char*)(0x8bee)); }


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 23, 2019, 03:07:19 am
I checked a bit further:
Edit2: scrap previous post

Interestingly, reading from IHRCAL, BGTCAL does not change the accu at all. This is why I was led to believe they would read the same values, because the accu still retained the value from reading the flash locations. Indeed, it is necessary to read the calibration manually.

A bit more compact macro:

#define PFS154_USE_FACTORY_TRIMMING() { __asm__ (".word (0x3fed)\nmov _ihrcr,a\n.word (0x3fee)\nmov _bgtr,a\n"); }

The bandgap is probably also used by the oscillator, unless it uses a separate voltage reference. It's a good idea to trim it, too. The resolution is rather fine though, around 500mV across the entire 8 bit range of BGTR, ~2mV per count. I tested this by using the comparator and Vint_ref as reference. It may be a challenge to measure the voltage accurately enough.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 23, 2019, 09:13:09 am
The bandgap is probably also used by the oscillator, unless it uses a separate voltage reference. It's a good idea to trim it, too. The resolution is rather fine though, around 500mV across the entire 8 bit range of BGTR, ~2mV per count. I tested this by using the comparator and Vint_ref as reference. It may be a challenge to measure the voltage accurately enough.

My plan is to use VDD and VBandgap as inputs for the comparator, send the comparator output to the dedicated output pin and capture this with programmer.
-> we can setup VDD with programmer an measure it with the programmer ADC very precise
-> by selecting a good "case" / "N" in GPCS / GPCR we should be able to do a simple and accurate trimming

I prepared a table for selecting a good value (see picture below).

The places with red VDD values are unusable for trimming. Unfortunately there is no 5.0 V possibility.

So we need to use "near requested VDD" values for trimming (e.g. 4.8V for 5.0V trimming).

I think "case 3", is suitable for all trimmings.

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: illiseon on September 23, 2019, 10:41:56 am
hello js:
         I do not understand how you use SPI to calibrate IC and measure the final frequency;Another thing I'm curious about is that there are direct ways to operate on OTP ram, such as burning programs directly into OTP ram and executing programs in ram.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 23, 2019, 05:21:05 pm
Apparently only bits [7:3] of BGTR are used. I determined Vbg to be at ~1.08V for BGTR=0 and 1.47V for BGTR=240 on one PFS154. This means that the voltage resolution of the trimming register is 8*(1.47V-1.08V)/240= ~ 13mV.

To reach a trimming accuracy that is better than 13mV it would be necessary to apply 4.8V+-26mV externally  (13*4.8/1.2/2=26). This assumes perfect resistor matching, which is unlikely. Certainly not impossible but also not without a challenge. If this is not possible it may be better to use the factory trimming.

A more accurate solution is obviously to apply 1.2V+-6.5mV to an external input of the comparator and use that as a trimming reference.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 23, 2019, 06:47:13 pm
I do not understand how you use SPI to calibrate IC and measure the final frequency.

This is a simple trick: SPI is enabled on easy pdk programmer as slave. This means the clock is generated from IC. Now you just start a precision timer and use SPI to receive several thousand bytes (8 bit each) from IC.
After a specific amount of clocks (bytes) was received from SPI you check the timer value and now you know how many clocks in what time been sent form IC.
Like this we can measure very high frequencies (>10 MHz, since SPI is in hardware on the easy pdk programmer MCU) and we also can use the SPI transmit line to send single pulses to the IC to change the tuning value.

Another thing I'm curious about is that there are direct ways to operate on OTP ram, such as burning programs directly into OTP ram and executing programs in ram.

The Padauk IC do not allow to execute from RAM. Also RAM is so tiny tiny small (64-256 byte) that you would not have the space to fit a lot of instructions inside.
However there are FLASH based Padauk ICs like PFS154 and PFS173 which can be erased and written many times (>1000 times). This are the ICs we usually use for development.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 23, 2019, 06:52:57 pm
Apparently only bits [7:3] of BGTR are used. I determined Vbg to be at ~1.08V for BGTR=0 and 1.47V for BGTR=240 on one PFS154. This means that the voltage resolution of the trimming register is 8*(1.47V-1.08V)/240= ~ 13mV.

To reach a trimming accuracy that is better than 13mV it would be necessary to apply 4.8V+-26mV externally  (13*4.8/1.2/2=26). This assumes perfect resistor matching, which is unlikely. Certainly not impossible but also not without a challenge. If this is not possible it may be better to use the factory trimming.

A more accurate solution is obviously to apply 1.2V+-6.5mV to an external input of the comparator and use that as a trimming reference.

Hi,

I think you look to precise on this. In order to understand the magnitude of error our cheap ICs are having I suggest the following experiments:

1) output an alternating clock signal on an IO pin and measure frequency with oscilloscope
2) now touch the IC with your finger (which slightly increases temperature) and watch the HUGE difference of the clock

3) tune and perform your band gap comparator test (e.g. switch at 1.200V)
4) now touch the IC with your finger (which slightly increases temperature) and watch the HUGE difference of the band gap switch

...

BTW: I found factory trimming of bandgap on all FLASH and some OTP variants, however factory trimming of IHRC is available on FLASH based ICs only. ILRC does not have a factory trimming values in any of the devices I checked.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 24, 2019, 08:50:16 am
JS earlier you told you have a good sample on generating sound with these babies? is it ready? also please add more examples to the repo, like, ADC,I2C,SPI etc... :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 25, 2019, 04:49:09 pm

Hi,

I think you look to precise on this. In order to understand the magnitude of error our cheap ICs are having I suggest the following experiments:

1) output an alternating clock signal on an IO pin and measure frequency with oscilloscope
2) now touch the IC with your finger (which slightly increases temperature) and watch the HUGE difference of the clock

3) tune and perform your band gap comparator test (e.g. switch at 1.200V)
4) now touch the IC with your finger (which slightly increases temperature) and watch the HUGE difference of the band gap switch

BTW: I found factory trimming of bandgap on all FLASH and some OTP variants, however factory trimming of IHRC is available on FLASH based ICs only. ILRC does not have a factory trimming values in any of the devices I checked.


Well, the lower end Padauks probably don't have an LDO to save die space, which means the PSRR is not good. That could explain why they react to touch. At least according ot the datasheet, the temperature drift of the IHRC is not that bad? They cut corners everywhere to reduce die area. I notitced that also the souring capability of the GPIO is much worse than other MCUs. Probably a way to avoid large I/O transistors.

My point about the band gap trimming is that it will not be easy to do it better than the factory calibration. Trimming on the prgrammer would only improve if you want to trim the band gap to a value different from 1.2V.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 29, 2019, 10:03:35 am
I can only corroberate JS findings about very bad noise immunity of the PFS154.

I wasted a lof time getting a LED to work as a light sensor on the PFS154. My only conclusion is that the PFS154 has severe internal coupling issues. I summarized my findings here:

https://cpldcpu.wordpress.com/2019/09/28/a-led-candle-based-on-the-3-cent-mcu/

It seems to be advised to stick to purely digital designs, at least for the lower end Padauk MCUs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 29, 2019, 10:12:36 am
Btw, here is an example to control WS2812 LEDs using SDCC:

https://github.com/cpldcpu/SimPad/tree/master/Toolchain/examples/WS2812_blinky
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on September 29, 2019, 01:58:03 pm
One quick question: has been the read protection of the PFS154 already documented? I want to build a tiny device and sell it, and I'd like to protect it, but I've not seen how the "code options" such as LVR voltage, code protection, etc... is programmed in.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jhpadjustable on September 30, 2019, 02:54:53 am
One quick question: has been the read protection of the PFS154 already documented?
Found this with a quick search of the thread: https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2305515/#msg2305515 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2305515/#msg2305515)
Also see https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt (https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 30, 2019, 04:15:44 pm
I can only corroberate JS findings about very bad noise immunity of the PFS154.

I wasted a lof time getting a LED to work as a light sensor on the PFS154. My only conclusion is that the PFS154 has severe internal coupling issues. I summarized my findings here:

https://cpldcpu.wordpress.com/2019/09/28/a-led-candle-based-on-the-3-cent-mcu/

It seems to be advised to stick to purely digital designs, at least for the lower end Padauk MCUs.

Bad noise immunity on the PFS series is not a surprise, it is even stated by Padauk in their catalog. The otherwise closest devices, but with claimed much better noise immunity would be the PFC series. Though teh PFC154 is marked as a "new" device, so it might take a few weeks until it arrives at distributors.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 02, 2019, 05:47:14 am
Bad noise immunity on the PFS series is not a surprise, it is even stated by Padauk in their catalog. The otherwise closest devices, but with claimed much better noise immunity would be the PFC series. Though teh PFC154 is marked as a "new" device, so it might take a few weeks until it arrives at distributors.

Yeah, it's kinda telling if the manufacturer mentions it even on their line card. Although, bad PSRR/EMI immunity does not neccesarily imply that there is also strong internal coupling. In this case it seems to be like that.

I wonder, has anybody tried the ADC in the PFS173 yet? How many bits are actually noise free?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 03, 2019, 06:37:06 pm
I've tried setting the last word but it seems there's some kind of either protection or sorcery going on - I cannot change it to anything:

Code: [Select]
> write-pfs154.py honk.ihx com3
Writing 0000-0007... done
Writing 0010-00AB... done
Writing 07FF-07FF... done
Verifying 0000-0007... OK
Verifying 0010-00AB... OK
Verifying 07FF-07FF... FAILED
@ 07FF - expected 0000, read 3FFF

I have VPP set to 5.8V and the rest of the flash seems to be programmable just fine. Should I do anything special to program this last word?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2019, 09:44:55 am
I've tried setting the last word but it seems there's some kind of either protection or sorcery going on - I cannot change it to anything:

Code: [Select]
> write-pfs154.py honk.ihx com3
Writing 0000-0007... done
Writing 0010-00AB... done
Writing 07FF-07FF... done
Verifying 0000-0007... OK
Verifying 0010-00AB... OK
Verifying 07FF-07FF... FAILED
@ 07FF - expected 0000, read 3FFF

I have VPP set to 5.8V and the rest of the flash seems to be programmable just fine. Should I do anything special to program this last word?

There is no magic for last word. It looks like your programmer / programming script tries to write to odd address. PFS devices only can start writing at even addresses (this means you have to write 7FE and 7FF, you can write "FFFF" to 7FE so it will not change the exisiting value, just the verifier in your script needs to know about this fact afterwards).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2019, 09:49:53 am
Bad noise immunity on the PFS series is not a surprise, it is even stated by Padauk in their catalog. The otherwise closest devices, but with claimed much better noise immunity would be the PFC series. Though teh PFC154 is marked as a "new" device, so it might take a few weeks until it arrives at distributors.

Yeah, it's kinda telling if the manufacturer mentions it even on their line card. Although, bad PSRR/EMI immunity does not neccesarily imply that there is also strong internal coupling. In this case it seems to be like that.

I wonder, has anybody tried the ADC in the PFS173 yet? How many bits are actually noise free?

I think PFS173 is the better way to go for your specific project.

I got PFS173 in small 6 pin housing for 4.6 cent / pcs. So no real need for me to use PFS154 or PMS150C:  https://item.taobao.com/item.htm?id=598420620199

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 04, 2019, 10:03:29 am
There is no magic for last word. It looks like your programmer / programming script tries to write to odd address. PFS devices only can start writing at even addresses (this means you have to write 7FE and 7FF, you can write "FFFF" to 7FE so it will not change the exisiting value, just the verifier in your script needs to know about this fact afterwards).

JS
Thank you! I will try to have my programmer align to chunks of 4 words.

EDIT: that did the job! Thank you again!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 04, 2019, 01:28:35 pm
As oposed to what https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt says, the LVR seems not to be configured via the last word but the MISC_LVR register:

For 4.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x00
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 3.5V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x20
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 3.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x40
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.75V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x60
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.5V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x80
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 1.8V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xA0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.2V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xC0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xE0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 04, 2019, 01:54:56 pm
I think PFS173 is the better way to go for your specific project.

I got PFS173 in small 6 pin housing for 4.6 cent / pcs. So no real need for me to use PFS154 or PMS150C:  https://item.taobao.com/item.htm?id=598420620199

JS

Thats a very good offer. How did you manage to order there?

I tried to investigate the PFS173 ADC only to find that ASPDK15 does not encode the SWAPC instruciton correctly, which is used in my softuart. Took quite a while to find this. Ticket to SDCC is submitted. Obviously, SDCC never generates a SWAPC, so it is not covered in the regression tests...


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2019, 06:38:01 pm
As oposed to what https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt says, the LVR seems not to be configured via the last word but the MISC_LVR register:

For 4.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x00
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 3.5V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x20
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 3.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x40
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.75V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x60
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.5V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0x80
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 1.8V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xA0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.2V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xC0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

For 2.0V:
Code: [Select]
0x0007:   0x2fe0    MOV A, 0xE0
0x0008:   0x019b    MOV IO(0x1B), A  ;MISC_LVR

Depends on the IC. The raw (very early) notes reference PMC154B with some similarities from PFS154. PMC154B does not have MISC_LVR register.

A better way is to use the original IDE, play with the "code options" for your specific CPU and document the results.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2019, 06:41:59 pm
I think PFS173 is the better way to go for your specific project.

I got PFS173 in small 6 pin housing for 4.6 cent / pcs. So no real need for me to use PFS154 or PMS150C:  https://item.taobao.com/item.htm?id=598420620199

JS

Thats a very good offer. How did you manage to order there?


I know some local guys ordering it for me and forward it.

But now that we know it exists: It is possible to query LCSC.com to get special parts which they do not have in inventory...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 06, 2019, 09:46:12 am
Regarding the MISC_LVR register again - was that name found somewhere in official PADAUK docs or in the IDE code or somewhere else? I am wondering because otherwise, maybe it would be sensible to rename it to MISCLVR (without the underscore), or lvrc (LVR control, as other control registers are the name of the peripheral + "c" such as tm2c or gpcc).

The problem with MISC_LVR is that I wanted to make a PR to cpldcpu's io_pfs154.h (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/pdk/io_pfs154.h) to include the bits that the IDE generates for several voltages for the PFS154 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2723562/#msg2723562), but there's already a MISC_LVR_DISABLE, and IMHO it would be confusing that this one refers to the misc register, and MISC_LVR_1_8V (for setting LVR to 1.8V, for example) refers to the MISC_LVR register.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 06, 2019, 10:29:37 am
Regarding the MISC_LVR register again - was that name found somewhere in official PADAUK docs or in the IDE code or somewhere else? I am wondering because otherwise, maybe it would be sensible to rename it to MISCLVR (without the underscore), or lvrc (LVR control, as other control registers are the name of the peripheral + "c" such as tm2c or gpcc).

The problem with MISC_LVR is that I wanted to make a PR to cpldcpu's io_pfs154.h (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/pdk/io_pfs154.h) to include the bits that the IDE generates for several voltages for the PFS154 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2723562/#msg2723562), but there's already a MISC_LVR_DISABLE, and IMHO it would be confusing that this one refers to the misc register, and MISC_LVR_1_8V (for setting LVR to 1.8V, for example) refers to the MISC_LVR register.

It's called like that in the official include for from the IDE (PFC154.INC), see below. The underscore does not fit to general conventions indeed.

JS has included the underscore in the defines.
https://github.com/free-pdk/easy-pdk-programmer-software/blob/master/Examples/src/easypdk/pfs154.h#L195 (https://github.com/free-pdk/easy-pdk-programmer-software/blob/master/Examples/src/easypdk/pfs154.h#L195)

Code: [Select]

MISC_LVR IO_WO:OP 0x1B (-)
$ 7 ~ 4 : 1V8, 1V9, 2V, 2V1, 2V2, 2V3, 2V4, 2V5, 2V75, 3V, 3V15, 3V3, 3V5, 3V75, 4V, 4V5
$ 1 ~ 0 : BG_On, BG/4, BG/32, BG_Auto
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on October 07, 2019, 07:20:18 pm
Maybe i missed this somewhere, but im not seeing it in the documentation.

I built the programmer, flashed firmware. All seems well.  I would like to program the 6 pin PMS150c, but i do not know how to wire to the output headers.  I have the PMS150 on a breakout board stuck into a bread board, with the intent to run jumper wires from the headers to the breadboard.  Any guidance would be appreciated.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on October 07, 2019, 08:12:19 pm
Maybe i missed this somewhere, but im not seeing it in the documentation.

I built the programmer, flashed firmware. All seems well.  I would like to program the 6 pin PMS150c, but i do not know how to wire to the output headers.
It is documented vaguely in the datasheets and manual for the official programmer from Padauk. You'd have to read several of the controller datasheets, the protocol description in this thread and on github and then slowly the pieces begin to fall together.

But I also made an adapter pcb which should make it easy: https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs (https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs). You could replicate that on your breadboard. See the schematics. The inner columns are the programmer, the outer ones the Padauk.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: chaplin on October 08, 2019, 03:26:00 am
hi,
i build my own easy-pdk-programmer  , but can't write ,Other operations are OK。
[attach=1]
this my board pic

any idea what might goes wrong?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 08, 2019, 04:13:19 pm
hi,
i build my own easy-pdk-programmer  , but can't write ,Other operations are OK。
(Attachment Link)
this my board pic

any idea what might goes wrong?

Hi,

it looks very good already.

The problem you see can be caused by long wires / dirty contacts of adapter / ... so VDD or VPP is not supplied properly to IC.
Usually reseating the IC in socket / using shorter wires solves this problem.

How do you connect the PFS173 to the programmer?


Also please check values and soldering of:
 C2 / C10 (must be 100nF, they stabilize VDD and VPP)
and
 C13 / C21 (must be 4.7uF, they stabilize the opamp inputs)

JS



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on October 08, 2019, 04:18:26 pm
Maybe i missed this somewhere, but im not seeing it in the documentation.

I built the programmer, flashed firmware. All seems well.  I would like to program the 6 pin PMS150c, but i do not know how to wire to the output headers.
It is documented vaguely in the datasheets and manual for the official programmer from Padauk. You'd have to read several of the controller datasheets, the protocol description in this thread and on github and then slowly the pieces begin to fall together.

But I also made an adapter pcb which should make it easy: https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs (https://github.com/free-pdk/easy-pdk-programmer-hardware/tree/master/adapter-pcbs). You could replicate that on your breadboard. See the schematics. The inner columns are the programmer, the outer ones the Padauk.


Oh ok good.  I can work with that.  I just realized based on the photos in the above post that the pins are meant to be marked on the PCB.  The silkscreening on my PCB is so bad that it all looks like smudges ha.  Thats what threw me for sure.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: chaplin on October 09, 2019, 08:57:06 am
hi,
i build my own easy-pdk-programmer  , but can't write ,Other operations are OK。
(Attachment Link)
this my board pic

any idea what might goes wrong?

Hi,

it looks very good already.

The problem you see can be caused by long wires / dirty contacts of adapter / ... so VDD or VPP is not supplied properly to IC.
Usually reseating the IC in socket / using shorter wires solves this problem.

How do you connect the PFS173 to the programmer?


Also please check values and soldering of:
 C2 / C10 (must be 100nF, they stabilize VDD and VPP)
and
 C13 / C21 (must be 4.7uF, they stabilize the opamp inputs)

JS
thanks JS,
I made a test board,  only PFS173 and Female Socket were soldered. I also checked   C2 / C10,C13 / C21 , and they were correct.
[attach=1]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 09, 2019, 03:56:49 pm
hi,
i build my own easy-pdk-programmer  , but can't write ,Other operations are OK。
(Attachment Link)
this my board pic

any idea what might goes wrong?

Hi,

it looks very good already.

The problem you see can be caused by long wires / dirty contacts of adapter / ... so VDD or VPP is not supplied properly to IC.
Usually reseating the IC in socket / using shorter wires solves this problem.

How do you connect the PFS173 to the programmer?


Also please check values and soldering of:
 C2 / C10 (must be 100nF, they stabilize VDD and VPP)
and
 C13 / C21 (must be 4.7uF, they stabilize the opamp inputs)

JS
thanks JS,
I made a test board,  only PFS173 and Female Socket were soldered. I also checked   C2 / C10,C13 / C21 , and they were correct.
(Attachment Link)

Hi,

On your test board you added more capacitors. This can cause the problem. With additional caps VPP and VDD might need more time / need to be a tiny bit higher to stabilize.
Could you try your extra test board without the capacitors?

Also which version of the programmer software + firmware do you use?
Latest 1.1 version (https://github.com/free-pdk/easy-pdk-programmer-software/releases) contains some improvements regarding writing of PFS173.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on October 09, 2019, 07:32:10 pm
ok ive made a little progress.  Programer is detected, chip is detected and id.  when i try to program the hello world 150c i get a successful write, but a failed verify.    if i try to write again it says chip is not blank (of course)

Running easypdk start i do not get a hello world, but i dont know if i am supposed to.

Not sure how to debug this. Running verbose doesn't seem to give anything further.   Tried 2 chips with same result just to make sure.

Also, what are these IHX files all about?  How does one convert a PDK project made in the official IDE to this format?

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 10, 2019, 07:17:53 am
ok ive made a little progress.  Programer is detected, chip is detected and id.  when i try to program the hello world 150c i get a successful write, but a failed verify.    if i try to write again it says chip is not blank (of course)

Running easypdk start i do not get a hello world, but i dont know if i am supposed to.

Not sure how to debug this. Running verbose doesn't seem to give anything further.   Tried 2 chips with same result just to make sure.

Also, what are these IHX files all about?  How does one convert a PDK project made in the official IDE to this format?

As mentioned before, the symptoms could be due to too much capacitance across VDD or sue to the user of an older version of the programmer software.
The programmer should work fine with the Padauk-recommended maximum of 0.01 µF though.

.ihx is Intel Hex, a rather common format (SDCC emits .ihx by default; the Padauk Mini-C IDE uses some weird obfuscated non-standard thing instead).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 10, 2019, 12:34:58 pm
ok ive made a little progress.  Programer is detected, chip is detected and id.  when i try to program the hello world 150c i get a successful write, but a failed verify.    if i try to write again it says chip is not blank (of course)

Running easypdk start i do not get a hello world, but i dont know if i am supposed to.

Not sure how to debug this. Running verbose doesn't seem to give anything further.   Tried 2 chips with same result just to make sure.

Also, what are these IHX files all about?  How does one convert a PDK project made in the official IDE to this format?

Hi,

can you try to read the written IC and check what was actually written?

You also can disable the blank check and try to write the IC again with the same file (see command line option of easypdkprog: --noblankchk). In case some bits not been written in the first run this can fix this situation.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 10, 2019, 04:17:52 pm
Regarding the MISC_LVR register again - was that name found somewhere in official PADAUK docs or in the IDE code or somewhere else? I am wondering because otherwise, maybe it would be sensible to rename it to MISCLVR (without the underscore), or lvrc (LVR control, as other control registers are the name of the peripheral + "c" such as tm2c or gpcc).

The problem with MISC_LVR is that I wanted to make a PR to cpldcpu's io_pfs154.h (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/pdk/io_pfs154.h) to include the bits that the IDE generates for several voltages for the PFS154 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2723562/#msg2723562), but there's already a MISC_LVR_DISABLE, and IMHO it would be confusing that this one refers to the misc register, and MISC_LVR_1_8V (for setting LVR to 1.8V, for example) refers to the MISC_LVR register.

Your argument with "MISC_LVR_DISABLE" confliction with "misc_lvr" register name was a good one.

I changed "_misc_lvr" to "_misclvr" and all its defines to "MISCLVR_...".

I also added defines in capital letters for all registers so Visual Studio Code can syntax highlight them (as suggested by @tim_). So for example the "_misc_lvr" register can be accessed by "MISCLVR" now, like: MISCLVR = MISCLVR_3V | MISCLVR_BANDGAP_AUTO;

(In development branch of programmer software, examples folder: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src))

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on October 10, 2019, 05:20:40 pm
I can read successfully and it has been written.  not sure how to compare it to input, since input is a IHX file, readout seems to do a HEX file or a BIN file.

no blank check yields a successful write and failed verify. Even running several times.

What is the hello world supposed to do? That is to say, how can i test that it is functioning? i assume a hello world over serial, but this does not happen.

Wirelength is about 10CM.  Anyway to slow down programming, in case wire length is an issue? it could be 100X slower and that would be just fine with me.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 11, 2019, 06:55:11 am
I can read successfully and it has been written.  not sure how to compare it to input, since input is a IHX file, readout seems to do a HEX file or a BIN file.

.ihx and .hex are both file endings for Intel Hex. objcopy can be used to convert between Intel Hex and raw binary.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on October 11, 2019, 03:54:22 pm
I can read successfully and it has been written.  not sure how to compare it to input, since input is a IHX file, readout seems to do a HEX file or a BIN file.

.ihx and .hex are both file endings for Intel Hex. objcopy can be used to convert between Intel Hex and raw binary.

I have attached my readout as well as the orginal example PM150 hello world (had to add txt per forum upload rules)

In hex editor they appear very different. 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 11, 2019, 10:35:03 pm
(In development branch of programmer software, examples folder: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src))

JS
I might be wrong, but isn't 2.5 LVR register value 0x80 instead of 0x70? I think I got 0x80, and that would make sense given the rest of the values are using only the three MSB of the MISCLVR register.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 12, 2019, 10:41:03 am
For quicker reference, here's a sorted table of all the VDD the comparator on the PFS154 can measure:

VDD (BG=1.2V)GPCS.5GPCS.4GPCS.N
1.600015
1.670014
1.750013
1.800115
1.830012
1.920114
1.920011
2.001015
2.020010
2.060113
2.091014
2.13009
2.181013
2.220112
2.26008
2.291012
2.40007
2.400111
2.401011
2.401115
2.531010
2.56006
2.561114
2.620110
2.67109
2.74005
2.741113
2.82108
2.88019
2.95004
2.951112
3.00107
3.20003
3.20018
3.201111
3.20106
3.43105
3.49002
3.491110
3.60017
3.69104
3.84001
3.84119
4.00103
4.11016
4.27000
4.27118
4.36102
4.80015
4.80101
4.80117
5.33100
5.49116
5.76014
6.40115
7.20013
7.68114
9.60012
9.60113
12.80112
14.40011
19.20111
28.80010
38.40110
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 12, 2019, 12:03:08 pm
I can read successfully and it has been written.  not sure how to compare it to input, since input is a IHX file, readout seems to do a HEX file or a BIN file.

.ihx and .hex are both file endings for Intel Hex. objcopy can be used to convert between Intel Hex and raw binary.

I have attached my readout as well as the orginal example PM150 hello world (had to add txt per forum upload rules)

In hex editor they appear very different.

Your "readout" file shows that only a few bits of the very first 2 words got changed. Most likely VDD / VPP was instable or inaccurate during programing.

In order to investigate further you should:
- check with "easypdkprogtest" the output values of VDD and VPP (nothing connected)
- check length / resistance of your wires / socket (it is not only the programing speed, also voltage is affected by poor / long / ... wires/sockets).
- show us a picture of your complete setup


JS

PS: The HelloWorld program will output "Hello World!" on the serial port. README in same directory as the .ihx files has full information:
https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 12, 2019, 03:23:52 pm
(In development branch of programmer software, examples folder: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src))

JS
I might be wrong, but isn't 2.5 LVR register value 0x80 instead of 0x70? I think I got 0x80, and that would make sense given the rest of the values are using only the three MSB of the MISCLVR register.

Hi,

according to the include file from IDE ("PFS173.INC") "misc_lvr" is defined like this:

MISC_LVR      IO_WO:OP   0x28 (-)
      $ 7 ~ 4 :   1V8, 1V9, 2V, 2V1, 2V2, 2V3, 2V4, 2V5, 2V75, 3V, 3V15, 3V3, 3V5, 3V75, 4V, 4V5
      $ 1 ~ 0   :   BG_On, BG/4, BG/32, BG_Auto


which translates to (bit 7-4 = upper most 4 bits = upper nibble):
1V8  = 0000rrxx = 0x00
1V9  = 0001rrxx = 0x10
2V    = 0010rrxx = 0x20
2V1  = 0011rrxx = 0x30
2V2  = 0100rrxx = 0x40
2V3  = 0101rrxx = 0x50
2V4  = 0110rrxx = 0x60
2V5  = 0111rrxx = 0x70  <== correct
2V75= 1000rrxx = 0x80
...


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 12, 2019, 03:35:08 pm
Sorry, I forgot to mention I was talking about the PFS154.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 12, 2019, 04:55:40 pm
Sorry, I forgot to mention I was talking about the PFS154.

Ok, now I see. It is fixed in development branch. Thanks for reporting.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 14, 2019, 03:31:49 pm
For a very low-power, which does not need perfect frequency accuracy, I'm trying to use ILRC and keep IHRC disabled. However I seem to be getting a frequency four times lower than expected on ILRC:

Code: [Select]
#include <pfs154.h>

// From cpldcpu's SimPad repository
#define PDK_USE_FACTORY_TRIMMING() {__asm__ (".word (0x3fed)\nmov __ihrcr,a\n.word (0x3fee)\nmov __bgtr,a\n");}

unsigned char _sdcc_external_startup(void) {
PDK_USE_FACTORY_TRIMMING();

// Set clock to ILRC and disable IHRC
CLKMD = CLKMD_ENABLE_ILRC | CLKMD_ENABLE_IHRC | CLKMD_ILRC;
CLKMD &= ~CLKMD_ENABLE_IHRC;

return 0;
}

int main(void) {
// Set PA0 pin to output
PAC = 0b00000001;

while (1) {
__set1(PA, 0);
__set0(PA, 0);
}
}
I get a square wave with a duty cycle of 25%, but at 11.1KHz rather than the expected 54KHz than the datasheet suggests. Any idea why?

I have tried with two different PFS154 to rule out a defect in a single device, and they both behave the same.

Hi,

this is exact what it should look like (according to your program).

After compilation have a look inside of the .asm file created from sdcc:

...
; ilrctest.c: 20: while (1) {
00102$:
; ilrctest.c: 21: __set1(PA, 0);
  set1  __pa, #0
; ilrctest.c: 22: __set0(PA, 0);
  set0  __pa, #0
  goto  00102$
...


set1 (1 cycle)
set0 (1 cycle)
goto (2 cycles)

==> 4 cycles per loop, set1 stays on for 1 cycle (25%) and set0 stays on for 1 + 2(goto) cycles (75%)

According to PFS154 data sheet chapter 4.4: ILRC is apx. 55kHz at 5.0V

==> 55000 Hz / 4 cycles = 13750 Hz (already very close to your measured output frequency, maybe ILRC also needs tuning which I have not finished in easypdkprog completely yet).

JS

BTW: ILRC is on by default (IC starts up with ILRC). There is no need to turn on IHRC and turn it off in _sdcc_external_startup. Also the factory trimming is for IHRC only, so there is no need to load it in this case.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on October 14, 2019, 03:41:56 pm
No no, I meant 11.1KHz CPU clock frequency, so about 2.77KHz frequency on PA0.

It turns out it was the scope's fault. Or maybe mine, depending on how you see it: last time I used it I was working with high speed signals instead of the slow signals I use to work with, so I used the "X5" magnification which I never use and forgot to turn it off  :palm:

Mix that with me getting the calculations incorrectly for the timer 2 by a factor of four in the program I had written before to blink an LED at about 0.5Hz, and you get me going crazy for the last three hours without knowing why every signal coming from the PFS154 is suddenly way slower than last week.

Thanks for your post still, though!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on October 25, 2019, 09:16:20 am
Hello :),

I hope that you can help me. I got to know the padauk uC from youtube quite a while ago. Recently I build the Free pdk Programmer from Github, but I have some starting issues. I got the firmware sucessfully flashed and have also probed successfully a PMS150C. My question is now what mikrocontrollers are supported by the time, bcause I think I read somewhere that I can only flash the PFS154 and PFS174. What format do I need for flashing? Do I need a .hex file or can I use the .pdk file of the padauk ide. If I could not use the .pdk file directly is there way to convert it to a .hex. If there is no way I have to use the SDCC for programming, don't I? And my last question is, if there is a tutorial or a list of the operations you can use when programming in c or mini-C?

I hope that you can help me.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 26, 2019, 03:23:06 pm
Hello :),

I hope that you can help me. I got to know the padauk uC from youtube quite a while ago. Recently I build the Free pdk Programmer from Github, but I have some starting issues. I got the firmware sucessfully flashed and have also probed successfully a PMS150C. My question is now what mikrocontrollers are supported by the time, bcause I think I read somewhere that I can only flash the PFS154 and PFS174.
Try
Code: [Select]
easypdkprog list to list the supported devices.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 26, 2019, 06:26:34 pm
And my last question is, if there is a tutorial or a list of the operations you can use when programming in c or mini-C?

When programming in C (that is using SDCC), nearly all of standard C will just work. Just learn C. Unless you run into code size / RAM size problems, if it compiles with GCC, it most likely will compile with SDCC.
You still need to think of the limitations of the hardware, and make sure you write efficient code, as otherwise you'll hit the hardware limits soon. Examples to get started can be found at: https://github.com/free-pdk/sdcc-pdk-code-examples

Mini-C, on the other hand is differerent. It ist just a thin layer above assembler with C-like syntax and very restricted. AFAIR, the documentation is somewhat outdated, and some of it is available in Traditional Chinese only. But there also are some examples that could help getting started.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on October 28, 2019, 06:17:39 am
Thank you for yours answers. I think I should have been a bit more specific. I am fairly expirience in programming with C (till now only Atmel controllers). I mean where do I find the specific comandos for setting up the uC. Thing like timer , interupts on coperator edge detections. Do I use the same aus discribed in the data sheet or do they vary a bit.

And the question for the programming of the PMS150C is more if I can generate the file for flashing or not? Therefor I want to know if I an use the .pdk Files from the padauk IDE. I think I read somewhere in this post, that by now only the PFS154 and PFS174 are supported in the SDCC and I can only flash .hex files because the .pdk contain futher informations than only the code (something like calibration of the clock).

I hope my questions are more understandable now.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 28, 2019, 09:41:02 am
Hi,

I mean where do I find the specific comandos for setting up the uC. Thing like timer , interupts on coperator edge detections. Do I use the same aus discribed in the data sheet or do they vary a bit.
The manufacturer data sheets are the best source. They explain in detail how to setup interrupts, timers, comparator, edge detections,...
As @spth mentioned before, there are several examples here: https://github.com/free-pdk/sdcc-pdk-code-examples
Also the easypdkprog repository contains a simple "hello world" example (compiled for PMS150C / PFS154 / PFS173 and as source code): https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples

And the question for the programming of the PMS150C is more if I can generate the file for flashing or not?
You can use SDCC and it will produce the complete (hex) file for flashing. (see above)

I think I read somewhere in this post, that by now only the PFS154 and PFS174 are supported in the SDCC...
This is wrong. Right now SDCC can be used to generate code for all 13, 14 and 15 bit PADAUK ICs which includes apx. 95% of all PADAUK ICs available.
It does not matter if they are OTP or flashed based.
PMS150 is 13 bit OTP
PMS154 is 14 bit OTP
PFS154 is 14 bit FLASH
PFS173 is 15 bit FLASH
...

So SDCC supports *all* ICs, easypdkprog needs to be extended for every specific IC. Right now the following IC types are supported:
./easypdkprog list
Supported ICs:
PMC251   (0x058): OTP  : 1024 (16 bit), RAM:  96 bytes
 PMS132   (0x109): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS132B  (0x109): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes
 PMS15A   (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes
 PMS152   (0xA27): OTP  : 1280 (14 bit), RAM:  80 bytes
 PMS271   (0xA58): OTP  : 1024 (16 bit), RAM:  64 bytes
 PFS154   (0xAA1): FLASH: 2048 (14 bit), RAM: 128 bytes
 PMS133   (0xC19): OTP  : 4096 (15 bit), RAM: 256 bytes
 PMS134   (0xC19): OTP  : 4096 (15 bit), RAM: 256 bytes
 MCU390   (0xC31): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS131   (0xC83): OTP  : 1536 (14 bit), RAM:  88 bytes
 PMS171B  (0xD36): OTP  : 1536 (14 bit), RAM:  96 bytes
 PMS154B  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PMS154C  (0xE06): OTP  : 2048 (14 bit), RAM: 128 bytes
 PFS173   (0xEA2): FLASH: 3072 (15 bit), RAM: 256 bytes


In case you need support for a specific IC not in the list just give a note.

Therefor I want to know if I an use the .pdk Files from the padauk IDE. I think I read ... that ... I can only flash .hex files because the .pdk contain futher informations than only the code (something like calibration of the clock).
This is correct. PDK files can NOT be flashed to the IC directly. The original IDE inserts a lot of stub code which the WRITER (flasher) needs to know about and manipulate the contents flashed to the IC.
For example The IDE inserts a a calibration loop in every PDK file which will prevent your program from starting unless you do a specific calibration and write some values to some special locations.
Since we focus on creating a free and open source tool chain here not much effort is going into adding support for the legacy closed and undocumented PDK file solution.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on October 31, 2019, 09:44:27 am
Hi

js_12345678_55AA you said tat the 13 bit padauks are supported, but on Github (https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/README) stands that it is still experimental. Futhermore I installed sdcc yesterday and only the pdk14 and pdk15 where showes for lib installation. Is there a way that I get the pdk13 lib, altthough it is still experimental. I want to use the PMS150C for a few small and very simple task, because of its little footprint (sot23-6).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 31, 2019, 06:51:15 pm
js_12345678_55AA you said tat the 13 bit padauks are supported, but on Github (https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/README (https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/README)) stands that it is still experimental.

Everything here is "experimental" ::). The text you reference is from June "For pdk13, the SDCC-based toolchain is still experimental as of 2019-06-09"). A lot has been done and SDCC produces good code for 13 bit. I used it for 2 full projects already.

Futhermore I installed sdcc yesterday and only the pdk14 and pdk15 where showes for lib installation.
Is there a way that I get the pdk13 lib, altthough it is still experimental.

If you follow the link / instructions from the example directory I mentioned earlier... https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src)
you will find a download link for current SDCC snapshots (nightly builds) for several platforms: http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)
I just checked again and 13 bit support is included.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 01, 2019, 11:29:50 am
The work you've done reverse-engineering and designing the programmer is very impressive  :). Is there a document describing the steps the programmer goes through to program the devices (e.g. set MCLR/Vpp=13V, VDD=6.5V, delay 100ms, etc.)?
Also, I was wondering if you've thought about using the PICKIT2 for programming the devices, as has a programmable Vpp/Vdd/etc. for programming PIC microcontrollers, and I get the feeling that the padauk chips are somewhat related. I've used the PICKIT2 for programming ATMEGA88 (set Vpp=Vdd=5V, use SPI data transfer) before the USBASP was readily available, and it may be easier to get hold of a PICKIT2 from online shops than the free-pdf/easy-pdk-programmer, for some people.

Best Regards,
db
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 01, 2019, 01:06:12 pm
The work you've done reverse-engineering and designing the programmer is very impressive  :). Is there a document describing the steps the programmer goes through to program the devices (e.g. set MCLR/Vpp=13V, VDD=6.5V, delay 100ms, etc.)?
Also, I was wondering if you've thought about using the PICKIT2 for programming the devices, as has a programmable Vpp/Vdd/etc. for programming PIC microcontrollers, and I get the feeling that the padauk chips are somewhat related. I've used the PICKIT2 for programming ATMEGA88 (set Vpp=Vdd=5V, use SPI data transfer) before the USBASP was readily available, and it may be easier to get hold of a PICKIT2 from online shops than the free-pdf/easy-pdk-programmer, for some people.

Best Regards,
db

Hi,

Have a look here: https://github.com/free-pdk/fppa-pdk-documentation . You will find many notes and documents regarding programing of the IC.

I also had a look at PICKIT2 and considered using it. Unfortunately it was not fulfilling all requirements like capturing high speed signal from IC (this is required to calibrate the internal oscillator).
Also the price of PICKIT2 is a bit high compared to the $2 solution of easypdk programmer  ::).

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 01, 2019, 01:28:49 pm
Have a look here: https://github.com/free-pdk/fppa-pdk-documentation . You will find many notes and documents regarding programing of the IC.
Thanks! The "Architectural considerations" document is quite thorough.

I also had a look at PICKIT2 and considered using it. Unfortunately it was not fulfilling all requirements like capturing high speed signal from IC (this is required to calibrate the internal oscillator).
The PICKIT2 can capture at up to 1MHz (or 500kHz, 250kHz, etc.), for 1000 samples, so the calibration should be possible. It can only output Vdd<5V though, which will be an issue if 6.5V is required for programming. This would require a hardware workaround, if 5V Vdd is insufficient.

Also the price of PICKIT2 is a bit high compared to the $2 solution of easypdk programmer  ::).
So, where/how would someone in a developing nation, in particular Australia, get one of these $2 programmers?

Cheers :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on November 01, 2019, 01:44:37 pm
There is a "limited voltage programming mode", at least for the PFS154, which does limit VDD to 5V. This mode is not yet documented however.

I would be interested too in using a PICkit too, since that would be an easier entry point for more people to get interested in the Padauk platform.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 01, 2019, 02:47:33 pm
Also the price of PICKIT2 is a bit high compared to the $2 solution of easypdk programmer  ::).
So, where/how would someone in a developing nation, in particular Australia, get one of these $2 programmers?

I outlined the process to order from JLCPCB.com and LCSC.com. If you use the signup discounts you might pay less than USD20 (including shipping) for several pcbs and parts to make at least 10 pcs... and it is a fun project to solder them :-)

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 01, 2019, 02:56:56 pm
There is a "limited voltage programming mode", at least for the PFS154, which does limit VDD to 5V. This mode is not yet documented however.

I would be interested too in using a PICkit too, since that would be an easier entry point for more people to get interested in the Padauk platform.

Hi,

according to PFS154 user manual we almost use "limited voltage programing mode...":

http://www.padauk.com.tw/upload/doc/PFS154%20datasheet_v104_EN_20190618.pdf (http://www.padauk.com.tw/upload/doc/PFS154%20datasheet_v104_EN_20190618.pdf)

Page 89:

The voltage conditions in Limited-Voltage programming mode:
  (1)VDD is 5.0V, and the maximum supply current is up to about 20mA.
  (2)PA5 is 8.0V.
  (3)The voltage of other program pins (except GND) is the same as VDD.


I used VDD 5.0V / VPP 8.0V before and it was working OK... But if you add a capacitor on VDD it causes problems. That's why it was increased VDD to 5.5V and VPP to 8.5V in current easypdkprog which worked out really well.
Maybe if you write slowly / multiple times the same word then you could make it work with 5.0V VDD. But anything lower than this (e.g. 4.9V) will not work for sure...
But this obviously would work for the PFS (flash based ICs) only.

JS


BTW: Have you seen this: https://github.com/free-pdk/easy-pdk-programmer-hardware/issues/10 (https://github.com/free-pdk/easy-pdk-programmer-hardware/issues/10)
Looks like somebody might create a ready made version and sell it soon...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 01, 2019, 05:46:18 pm
Hi

js_12345678_55AA you said tat the 13 bit padauks are supported, but on Github (https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/README (https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/README)) stands that it is still experimental. Futhermore I installed sdcc yesterday and only the pdk14 and pdk15 where showes for lib installation. Is there a way that I get the pdk13 lib, altthough it is still experimental. I want to use the PMS150C for a few small and very simple task, because of its little footprint (sot23-6).

Did you install a release version? If yes, the latest is 3.9.0 and does not yet support pdk13.
If you want pdk13 support, you need to install a current snapshot (http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)) or just compile from svn.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 01, 2019, 10:29:00 pm
I would be interested too in using a PICkit too, since that would be an easier entry point for more people to get interested in the Padauk platform.
Same. I might have a go, although the way I'm thinking will require an external power supply, and an opamp to multiply the VDD x1.5.
I outlined the process to order from JLCPCB.com and LCSC.com. If you use the signup discounts you might pay less than USD20 (including shipping) for several pcbs and parts to make at least 10 pcs... and it is a fun project to solder them :-)
Yes, I did see that; it's a bit more than just a $2 device then. Maybe if the taobao guy doesn't get up and running, I'll consider making a batch. Soldering new clean PCBs is always fun :)
But anything lower than this (e.g. 4.9V) will not work for sure...  But this obviously would work for the PFS (flash based ICs) only.
That's good to know about the LVPM; the PICKIT2 has a schottky diode in line with VDD, so it will be ~4.9V max (unless VUSB is boosted to 6V).
BTW: Have you seen this: https://github.com/free-pdk/easy-pdk-programmer-hardware/issues/10 (https://github.com/free-pdk/easy-pdk-programmer-hardware/issues/10)
Looks like somebody might create a ready made version and sell it soon...
Sounds good :)

Thanks for all the great replies!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on November 02, 2019, 09:12:01 am

If you follow the link / instructions from the example directory I mentioned earlier... https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src)
you will find a download link for current SDCC snapshots (nightly builds) for several platforms: http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)
I just checked again and 13 bit support is included.


Okay, I did what you said, but I still did not get it completly (sorry for that). I downloaded and installed the sdcc exe. During the installation prozess the applied libs are viewed. So I downloaded additionally the .zip file and unzipped it. In this unziped directory I found in the lib folder the pdk13 folder and copied it into the lib folder of the installed exe.
Now I tried compieling the code examples. At first helloword example from the software branch and later the examples from the sdcc example branch. Non of them worked. In the helloworld from the software branch I later defined additionally the the used uC. At first I tried compiling withe the "make" command in diffent variations like explained in the software/examples/src branch but I did not get a response at all. Next I tried compiling with "sdcc helloworld.c" . With this it started compiling but I got warning 182 for the "pfs154.h" "absolute address for sfr '...' probably out of range". Futhermore I got errors for helloworld.asm. Ten times I got ".org in REL area or directive / mnemonic error" and at last "missing or improper operator, terminators, or delimiters". After that helloworld.rel was removed. (I added a screenshot of the cmd window)

It would be great if you can tell me what I am doing wrong all the time and thank you very much for your comments in the past.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 02, 2019, 10:15:59 am

If you follow the link / instructions from the example directory I mentioned earlier... https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src (https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src)
you will find a download link for current SDCC snapshots (nightly builds) for several platforms: http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)
I just checked again and 13 bit support is included.


Okay, I did what you said, but I still did not get it completly (sorry for that). I downloaded and installed the sdcc exe. During the installation prozess the applied libs are viewed. So I downloaded additionally the .zip file and unzipped it. In this unziped directory I found in the lib folder the pdk13 folder and copied it into the lib folder of the installed exe.
Now I tried compieling the code examples. At first helloword example from the software branch and later the examples from the sdcc example branch. Non of them worked. In the helloworld from the software branch I later defined additionally the the used uC. At first I tried compiling withe the "make" command in diffent variations like explained in the software/examples/src branch but I did not get a response at all. Next I tried compiling with "sdcc helloworld.c" . With this it started compiling but I got warning 182 for the "pfs154.h" "absolute address for sfr '...' probably out of range". Futhermore I got errors for helloworld.asm. Ten times I got ".org in REL area or directive / mnemonic error" and at last "missing or improper operator, terminators, or delimiters". After that helloworld.rel was removed. (I added a screenshot of the cmd window)

It would be great if you can tell me what I am doing wrong all the time and thank you very much for your comments in the past.

I checked, and there indeed was a problem with the pdk13 library missing in the Windows installer. If I didn't make a mistake it should be fixed now, and tomorrow's installers should install the pdk13.lib correctly (but I am not familiar with Windows, and might have made a mistake).

Do you have "make" installed? AFAIK it is not included in Windows.

"sdcc helloworld.c" would try to compile for the default mcs51 target, MCS-51 (i.e. Intel 8051 and compatible). For Padauk, you need to specify the target, i.e. using the option -mpdk13, -mpdk14 or -mpdk15.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 02, 2019, 10:49:05 pm
Hi. I just had a look at the schematic.

Why is the supply switched to the boost converter, rather than using the 'Enable' pin of the converter? The extra 4u7 on the +5V rail is within USB spec's <10uF total rail capacitance.

Why is the negative charge pump required for the opamp? The AS358 input and output ranges include 0V. Was it added because the AS358 sink current drops off below 1V? I get the feeling that it shouldn't be an issue.

EDIT: also, I think the filter on the AS358A positive supply can be removed, as its PSRR is 100dB.

Cheers,
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 03, 2019, 11:31:07 am
Hi. I just had a look at the schematic.
Why is the supply switched to the boost converter, rather than using the 'Enable' pin of the converter? The extra 4u7 on the +5V rail is within USB spec's <10uF total rail capacitance.
It's for protection. The enable signal of the boost converter does not enable / disable the output. It is enabling / disabling the boost. So at startup, even without the enable signal present, you get +5V out of it.
The output of the boost converter directly feeds the opamp.
But at startup DAC output of the STM32 and the negative voltage reference of the opamp is undefined which would let the output of the boost converter slip through to the pins of a potential connected target IC.

To completely eliminate unpredictable voltage spikes at startup I decided to turn off the complete supply to the boost converter.
At startup, first DAC output and OPAMP negative reference is initialized and later on demand boost converter voltage rail is turned on.

Why is the negative charge pump required for the opamp? The AS358 input and output ranges include 0V. Was it added because the AS358 sink current drops off below 1V? I get the feeling that it shouldn't be an issue.

To save cost. I wanted to use a cheap opamp (rail to rail opamps are much more expensive) and we really need 0V. With a non rail to rail opamp like the AS358 it is impossible to get 0V output with a 0V negative reference.
That's why the variant with the 2 diodes + PWM to generate a negative voltage for the opamp negative reference was chosen.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 03, 2019, 12:07:53 pm
Thanks for the reply.  :)
It's for protection. The enable signal of the boost converter does not enable / disable the output. It is enabling / disabling the boost. So at startup, even without the enable signal present, you get +5V out of it.
The output of the boost converter directly feeds the opamp.
But at startup DAC output of the STM32 and the negative voltage reference of the opamp is undefined which would let the output of the boost converter slip through to the pins of a potential connected target IC.
The DAC pins are pulled low through 240k resistors, so on startup, the voltage is 0V. If the charge pump was removed, the negative voltage would always be stable.

To save cost. I wanted to use a cheap opamp (rail to rail opamps are much more expensive) and we really need 0V. With a non rail to rail opamp like the AS358 it is impossible to get 0V output with a 0V negative reference.
The AS358 has an output range of 0V to 13.5V, with a 15V supply voltage. The input voltage range also includes 0V. The only thing to note with the output voltage under 1V is that the current that the output can sink reduces rapidly.

I think you could remove 10 components and have it still function happily.

Cheers,
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 03, 2019, 12:38:08 pm
Thanks for the reply.  :)
It's for protection. The enable signal of the boost converter does not enable / disable the output. It is enabling / disabling the boost. So at startup, even without the enable signal present, you get +5V out of it.
The output of the boost converter directly feeds the opamp.
But at startup DAC output of the STM32 and the negative voltage reference of the opamp is undefined which would let the output of the boost converter slip through to the pins of a potential connected target IC.
The DAC pins are pulled low through 240k resistors, so on startup, the voltage is 0V. If the charge pump was removed, the negative voltage would always be stable.
Unfortunately not.... When you enable the DAC on STM32 the output is 100%. After initialization you can setup 0 value. So for a short moment DAC output is 100% during initialization.

To save cost. I wanted to use a cheap opamp (rail to rail opamps are much more expensive) and we really need 0V. With a non rail to rail opamp like the AS358 it is impossible to get 0V output with a 0V negative reference.
The AS358 has an output range of 0V to 13.5V, with a 15V supply voltage. The input voltage range also includes 0V. The only thing to note with the output voltage under 1V is that the current that the output can sink reduces rapidly.
I tried without the negative reference and could not program the ICs. I think the 2 extra diodes are ok... If I rememebr correctly I was never able to get 0V from opamp output with VIN- tied to GND. Have you tested / measured the result with AS358 and VIN- 0V?

I think you could remove 10 components and have it still function happily.
Cheers,

There are other places where you can remove a lot more components. E.g. the ADC feedback is not required for normal programing, the programmer would work without LEDs, the button is not required, some of the capacitors might be unnecessary, ... But all of them make things easier for debugging, and might come handy in future (stand alone programmer).


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 03, 2019, 12:51:58 pm
It sounds like you've already tested everything I've mentioned. I am surprised, though.
No, I haven't used AS358, but I have used LM358. I'll measure the output of the LM358 when I can find where I've put them.

Cheers,
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 03, 2019, 01:05:55 pm
It would be great if you can tell me what I am doing wrong all the time and thank you very much for your comments in the past.

Hi,

from your comments I see that you are not familiar with compiling from command line. Looks like you don't have a "make" program and you don't know about include / lib path traversal.

I created a step by step "walk through" how to install, setup, compile, write and test the Helloworld program on a regular Windows PC without any prerequisites:

Start CMD and create folder:

C:\>mkdir C:\freepdk

C:\>cd C:\freepdk

C:\freepdk>


Use a Browser to download files and unpack them:

Browser->Open: http://sdcc.sourceforge.net/snap.php (http://sdcc.sourceforge.net/snap.php)
Download: "sdcc-snapshot-i586-mingw32msvc-20191102-11444.zip"  (or latest, NOT THE SETUP)

Extract "sdcc-snapshot-i586-mingw32msvc-....ZIP" to "C:\freepdk"
=> Verify that you have "C:\freepdk\sdcc\bin\sdcc.exe" and "C:\freepdk\sdcc\lib\pdk13\pdk13.lib"

Browser->Open: https://github.com/free-pdk/easy-pdk-programmer-software/releases (https://github.com/free-pdk/easy-pdk-programmer-software/releases)
Download: "EASYPDKPROG_WIN_20190907_1.1.zip" (or latest)

Extract "EASYPDKPROG_WIN_....zip" to "C:\freepdk"
=> Verify that you have "C:\freepdk\EASYPDKPROG\easypdkprog.exe"


Now continue in CMD:

Compile the sources:
C:\freepdk>cd C:\freepdk\EASYPDKPROG\Examples\src

C:\freepdk\EASYPDKPROG\Examples\src>mkdir build

C:\freepdk\EASYPDKPROG\Examples\src>..\..\..\sdcc\bin\sdcc.exe -DPMS150C -mpdk13 -o build\helloworld_pms150c.ihx helloworld.c

C:\freepdk\EASYPDKPROG\Examples\src>..\..\..\sdcc\bin\sdcc.exe -DPFS154 -mpdk14 -o build\helloworld_pfs154.ihx helloworld.c

C:\freepdk\EASYPDKPROG\Examples\src>..\..\..\sdcc\bin\sdcc.exe -DPFS173 -mpdk15 -o build\helloworld_pfs173.ihx helloworld.c

=> Now you can find the compiled hex files (*.ihx) in folder "C:\freepdk\EASYPDKPROG\Examples\src\build"

Example: Connect programmer with a PFS154 on top.

Check for programmer and PFS154:
C:\freepdk\EASYPDKPROG\Examples\src>..\..\easypdkprog.exe probe
Probing IC... found.
TYPE:FLASH RSP:0xAA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1


Write PFS154:

C:\freepdk\EASYPDKPROG\Examples\src>..\..\easypdkprog.exe write build\helloworld_pfs154.ihx -nPFS154
Erasing IC... done.
Writing IC... done.
Calibrating IC (@4.00V IHRC SYSCLK=8000000Hz)... calibration result: 7991184Hz (0x81)  done.


Run PFS154:

C:\freepdk\EASYPDKPROG\Examples\src>..\..\easypdkprog.exe start --runvdd=4.0
Running IC (4.00V)... IC started, press [Esc] to stop.
Hello World!
Hello World!
Hello World!

IC stopped



Have fun,

JS

P.S. make sure that you really type in the complete bold text with all the dots and backslashes like ..\..\..\
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on November 03, 2019, 10:26:44 pm
If I rememebr correctly I was never able to get 0V from opamp output with VIN- tied to GND. Have you tested / measured the result with AS358 and VIN- 0V?
I just connected an LM358 as a unity-gain buffer, on a 12V supply, which gave ~6mV output for 0V input, and 10.76V for 12V input.

The TI LM358 and the DI AS358 datasheets have the same simplified schematics (transistors and current sources), and I suspect that they're effectively the same device.
Cheers,
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 03, 2019, 10:57:33 pm
If I rememebr correctly I was never able to get 0V from opamp output with VIN- tied to GND. Have you tested / measured the result with AS358 and VIN- 0V?
I just connected an LM358 as a unity-gain buffer, on a 12V supply, which gave ~6mV output for 0V input, and 10.76V for 12V input.

The TI LM358 and the DI AS358 datasheets have the same simplified schematics (transistors and current sources), and I suspect that they're effectively the same device.
Cheers,

Yes, 6mV at 0V input. But the DAC of the STM32 has a 35mV DC offset and then the output was to high (not 0 enough anymore).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on November 04, 2019, 10:21:05 pm
Hi,

thank you very, very much js_12345678_55AA. I think it would be great, if you add your walk trough to the github readme. I finally got it to work. Because I thought the operation through the command window is a bit annoying, I wrote a little GUI for easier operation.
With it you can compile your c Files and probe/erase/flash the microcontroller. Therefor you can selct your uC via a drop down list. At the time I have insertet the PMS150C, PFS154 and PFS174. If you want I could share the software on github. If so should I put into the easy-pdk-programmer-software branch?

Another big thank you for your great support :)
Title: Padauk Programmer LEDs
Post by: icraftcrafts on November 05, 2019, 07:09:11 pm
Hi everyone. Thanks all for your great work on this project.

I built the programmer and need some help getting my programmer working please. The firmware to stm32 flashed correctly. I have a few PMS150c 8 pins I can use and have it connected.  When i use easypdkprog I get the message "No programmer found".

What I'd like to know is, is there any component I may have botched? When do the LEDs light up? Are there testpoints I can check for certain voltages to know if i damaged something? I did handsolder and the stm32 suffered the most with my "skills" but it seems to be ok.

Any assistance in the right direction is appreciated.

ADDED: I'm using ubuntu 18.04
Title: Re: Padauk Programmer LEDs
Post by: js_12345678_55AA on November 06, 2019, 11:25:59 am
The firmware to stm32 flashed correctly. I have a few PMS150c 8 pins I can use and have it connected.  When i use easypdkprog I get the message "No programmer found".
How did you flash the firmware? With DFU tool over USB from your Ubuntu installation?
If so please provide the output to make sure the complete firmware was written correctly (incorrect / not written firmware will give you the "no programmer found" message later)
Output should look like this:

dfu-util 0.9
   ...
   Opening DFU capable USB device...
   ID 0483:df11
   Run-time device DFU version 011a
   Claiming USB DFU Interface...
   Setting Alternate Setting #0 ...
   Determining device status: state = dfuIDLE, status = 0
   dfuIDLE, continuing
   DFU mode device DFU version 011a
   Device returned transfer size 2048
   DfuSe interface name: "Internal Flash  "
   Downloading to address = 0x08000000, size = 27635
   Download  [=========================] 100%        27635 bytes
   Download done.
   File downloaded successfully


=> Do not forget to unplug / replug the programmer from USB after firmware update, otherwise it can not be recognized.

After checking firmware was flashed correctly, USB is confirmed working already :-)

Now connect the programmer and run "dmesg" (without the quotes) in terminal and provide output (only last 10 lines are interesting). It should look like this:
...
[  955.834095] usb 2-2.1: new full-speed USB device number 6 using uhci_hcd
[  956.066910] usb 2-2.1: New USB device found, idVendor=0483, idProduct=5740
[  956.066913] usb 2-2.1: New USB device strings: Mfr=1, Product=2, SerialNumber=3
[  956.066915] usb 2-2.1: Product: Easy PDK Programmer
[  956.066917] usb 2-2.1: Manufacturer: free-pdk.github.io
[  956.066918] usb 2-2.1: SerialNumber: 1234567855AA
[  956.106462] cdc_acm 2-2.1:1.0: ttyACM0: USB ACM device


You also can run "lsusb" (without the quotes) in terminal and provide the output. It should look like this:
Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 004 Device 001: ID 1d6b:0003 Linux Foundation 3.0 root hub
Bus 003 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub
Bus 002 Device 004: ID 0483:5740 STMicroelectronics STM32...
Bus 002 Device 001: ID 1d6b:0001 Linux Foundation 1.1 root hub


Next:
unplug the programmer and run "ls /dev/ttyACM*" (without the quotes). Output should be empty or show other serial ports attached to your system

connect programmer and run again "ls /dev/ttyACM*" (without the quotes). Output should show the serial port of programmer (any maybe other serial ports attached to your system):
/dev/ttyACM0

What I'd like to know is, is there any component I may have botched? When do the LEDs light up? Are there testpoints I can check for certain voltages to know if i damaged something? I did handsolder and the stm32 suffered the most with my "skills" but it seems to be ok.

The LEDs light up when easypdkprog is connected to the programmer and is doing some work. Just connecting the device to USB will not light the LEDs.
The schematic and PCB layout show the various voltage rails. But since you said you could write the firmware, you most likely do not have a short circuit / damaged component problem.

Can you take a good resolution picture of your PCB and attach it here? Maybe something can be spotted from the picture.

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: icraftcrafts on November 06, 2019, 02:32:48 pm
Thanks for your reply JS. Here's a screenshot of the dfu-util output. dmesg -c before and after replugging (after flash) is blank. dmesg when putting stm in bootloader mode shows the correct stm output. no lsusb changes after flash. also my byte size is different from your screen output.

[ADDED] i will try to post a high res pic this eve.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: icraftcrafts on November 06, 2019, 02:49:12 pm
shucks i actually see that dfu error only now   :palm:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 06, 2019, 02:59:25 pm
shucks i actually see that dfu error only now   :palm:

Hi,

i see some other things from DFU output:

1) a warning that your DFU file is not having a valid DFU suffix
2) your DFU file size (83kB) is much bigger than the current release firmware (28kB)

=> most likely you flashed the wrong file. Maybe you downloaded a HTML web site from github (this sometimes happens when you right-click in source view on a file and download it... this will download the following HTML page instead of the file).

A pre compiled DFU file is included in the RELEASE of the easypdk programmer software: https://github.com/free-pdk/easy-pdk-programmer-software/releases  - for your system: "EASYPDKPROG_LINUX_20190907_1.1.zip"


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: icraftcrafts on November 06, 2019, 03:22:20 pm
You are correct about incorrect file JS.It has html content. I've found the correct one in the firmware directory  :palm: :palm:

but success after a two day smd job. Im glad its working as im too embarassed to send a high res photo lol. heres the correct dmesg output below. I will get into trying the otp pms150c 8 pin as i have about 300 of them. i hope i can be of some assistance later on in this project. Thanks again JS :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: icraftcrafts on November 06, 2019, 03:50:21 pm
Im getting the below error when trying to flash the example code to the pms. led closest to side is blinking now  :).

I think i saw somewhere in one of the posts you mentioned something about cabling being too long. Im currently using 200mm dupont cables but will swap them later.

 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: icraftcrafts on November 06, 2019, 04:15:23 pm
Successful write and read. What i did was grab the bundle of wires together to sort of see if it creates a kind of shield or cancellation with ground or each other. Then i could manage to read it repeatedly with 200mm dupont wires. And the write was successful as can be seen in the output. Now i'd like to know if there's any way I can assist?

Regards.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: soFPG on November 16, 2019, 08:15:12 pm
Is there any reverse engineering regarding the ICE (In-Circuit-Emulator) going on (didn't read the whole 32 pages)?

If not, I attached a picture of the top side of the PCB - in case anyone is interested (attention: huge image).

Couldn't find any information about the SGD0235R3 IC in the center (which is upside-down at the moment because the top side doesn't have any text on it) - my guess is it is an FPGA.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: soFPG on November 16, 2019, 08:26:37 pm
and the backside.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: I wanted a rude username on November 21, 2019, 08:59:06 am
Is there any reverse engineering regarding the ICE (In-Circuit-Emulator) going on (didn't read the whole 32 pages)?

I got my ICE today as well. Here is a high resolution image: https://i.imgur.com/8yef37g.jpg (https://i.imgur.com/8yef37g.jpg)

The FPGA has no markings. It might be possible to capture the JTAG init sequence, if it doesn't store the configuration data inside the FPGA, because looks like there is no external configuration flash memory.

The USB device is a CY7C68013A, with high speed USB (480 Mbps) and an integrated 8051 CPU, that can be booted through USB (there is an interesting project, which implements a communication through such a Cypress chip to a FPGA over USB, FPGALink (http://www.swaton.ukfsn.org/docs/fpgalink/vhdl_paper.pdf)). So this could be a very flexible construction, booting first the firmware of the 8051, then booting the FPGA bitstream, all over USB. But I think it might be easier to develop a new emulator than trying to reverse engineer this. Would be nearly impossible to decode the FPGA bitstream back to the HDL code.

"usb-devices" shows the same as js_12345678_55AA wrote:

Code: [Select]
T:  Bus=01 Lev=01 Prnt=01 Port=01 Cnt=03 Dev#=  9 Spd=480 MxCh= 0                                                                                                                                             
D:  Ver= 2.00 Cls=00(>ifc ) Sub=00 Prot=00 MxPS=64 #Cfgs=  1                                                                                                                                                 
P:  Vendor=0797 ProdID=7002 Rev=80.01                                                                                                                                                                         
S:  Manufacturer=PADAUK                                                                                                                                                                                       
S:  Product=LGS_DEV FX2-HID 0.01                                                                                                                                                                             
C:  #Ifs= 1 Cfg#= 1 Atr=a0 MxPwr=500mA                                                                                                                                                                       
I:  If#= 0 Alt= 0 #EPs= 2 Cls=03(HID  ) Sub=00 Prot=00 Driver=usbhid   

(Emphasis added)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 26, 2019, 02:31:02 pm
JS I'm playing with your serialecho example, and modified it! I think the getchar is not working

here is the modified code , in the attached form

Please see the attached picture, it does not get anything and would stuck in the getchar in a loop, I have entered "w" and "q" in the terminal, and obviously it does not get anything from RX

Also Do you have some ADC examples?

I have written a simple makefile too, by juts running make run command, compilation, programming and running the device is done :)

Code: [Select]
# SDCC=../../sdcc/bin/sdcc
# Add enviroment path for SDCC to windows path
SDCC = sdcc.exe
OUTDIR=build

all: PFS173


PFS173:
mkdir -p $(OUTDIR)
$(SDCC) -DPFS173 -mpdk15 -o $(OUTDIR)/main.ihx main.c


clean:
rm -rf $(OUTDIR)

# Place easypdkprog.exe file inside the source folder of your .c file
prog:
easypdkprog write build\main.ihx -nPFS173

start:
@echo "Starting the Device"
easypdkprog start --runvdd=4.0

run: PFS173 prog start
.PHONY: all clean

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 26, 2019, 04:37:31 pm
JS I'm playing with your serialecho example, and modified it! I think the getchar is not working

Hi, I had a similar problem a few days ago with PFS173. Turns out PFS173 explicitly needs to setup digital inputs in the PxDIER (digital input enable register).
On PFS154 and PMS150C this is not needed.

So all you need to add is one line after setting up PAC:

  PADIER = 0x01;                                 //select PA.0 as digital input (required for PFS173)

The development branch has an updated example.
 
==> IMPORTANT FOR ALL:  PFS173 needs setup of PxDIER in case you want to use a digital input pin. PFS154/PMS150C do not need this but it will not harm to set it up as well <==

Also Do you have some ADC examples?

Not yet, but I work on something which needs the ADC.

Meanwhile have a look at CPLDCPUs git repo: https://github.com/cpldcpu/SimPad/blob/master/Toolchain/examples/ADC_PFS173/adc.c

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 27, 2019, 07:06:08 am
Thanks JS, you are a hero :-+

Also Please try to add the industrial grad parts support too. I mean the PMC series, with a Operating temperature range: -40°C ~ 85°C.
Personally I like the ones with integrated ADC like the PMC271,PMC131,PMC232,PMC234 parts, As they can be used in the Industrial field and they can be very useful,replacing many parts ^-^
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 27, 2019, 02:00:32 pm
JS, your example baud rate is completely wrong! I have connected the PFS173 to an external FTDI to USB chip to test it.

I should make the baudrate 28800 to be able to get the messages write! Also I think the RXD is working some how, It just get the first char correctly, but the subsequent ones are missed. see the attached picture.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 27, 2019, 02:10:16 pm
Also Please check this out the getchar is working but it would receive it wrong! instead of getting 0x61 which is an "a" char, it would receive  it like 0x27


Here is the main loop code from the serialio example

Code: [Select]
char c='';
for(;;)
  {
    puts("Echoing serial receive (type something):\r\n");
    for(int i=0;i<10000;i++);
    c = getchar();
    for(int i=0;i<10000;i++);
    putchar(c);
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 28, 2019, 12:22:06 pm
Also Do you have some ADC examples?

I added an ADC example (for PFS173) to the development branch.

It shows how to measure the ADC value of the internal BandGap voltage (VBG = 1.200V) which then can be used to calculate VDD:
VDD (?) => max value of ADC = 255
VBG (1.2V) => adcval

==> VDD = (1.2 * 255 ) / adcval

Then it shows how to measure input of PA.0. (Note: when running in easypdk programmer, PA.0 is pulled up to VDD of the programmer which is 3.3V).


Have fun,

JS


P.S. The serial echo sample is not finished yet. Looks like the interrupt takes way to many cycles. It either needs optimization or the BAUD rate needs to be lowered.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 28, 2019, 12:34:36 pm
Thanks JS, I think if we add a delay after puts, we would get the RX wrong! maybe there is a bug in the compiler.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on November 29, 2019, 06:01:38 pm
Hi,

I added more example programs to the easypdk programmer (in development branch: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples )

* COMPtest shows how to use the comparator to estimate VDD (good for battery based projects on ICs without ADC).

* PolySound is a fun project which uses PWM to play a polyphonic sound. It emulates a NES sound chip with 4 voices to play a music theme from Mega Man 2. It requires 182 bytes RAM and 2.1k words CODE (e.g. PFS173).
   You only need to connect a speaker to PA.3 and GND  :). Of course a low pass filter for the PWM would be much better.
   The original project was implemented for a PIC16 by Joel Yliluoma : https://bisqwit.iki.fi/jutut/kuvat/programming_examples/pic/
   To stay as close as possible to the original code, SYSCLK is tuned (overclocked) to 10MHz - which works absolutely fine  8)

   Attached is a sound file of the output (low pass filtered)  ;D

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 29, 2019, 09:16:43 pm
Thanks JS :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on December 12, 2019, 03:11:51 am
The depdk converted bin file cannot be written to the target chip using easypdkprog Is there a way to convert the bin file to an ihx file ?
Please forgive me for not understanding English. I translated it using google.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on December 12, 2019, 09:10:31 am
FYI, I ventured out and reviewed all sub $0.10 microcontrollers on LCSC. I hope it's somewhat useful:

https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/ (https://cpldcpu.wordpress.com/2019/08/12/the-terrible-3-cent-mcu/)

I can now confirm that the Padauk MCUs are the best in this segment. We knew this before, did we?

Well, now back to actual projects on the PFS154...
Cheap MCUs that are widely used in China are OTP produced by Taiwan nyquest. My purchase of NY8A050D is only RMB 0.1 yuan, about 0.014 US dollars.
nyquest website :   http://www.nyquest.com.tw/ (http://www.nyquest.com.tw/)
Attached is the NY8A050D&HR7P153 English Datasheet,Please accept.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on December 12, 2019, 11:07:31 am
Thanks JS, I managed to flash the Dev branch to the ARM and now it's working, But still only probing is working |O |O |O any Idea what might goes wrong?

Now you have to check your hardware variant. On the picture I saw that C1 is not populated and also Y1 is missing. A cap on the 15V rail is essential since VCC/VDD draw some power during programing. The crystal is used to get better tuning results after the CPU is flashed, without it the drift might be much higher or you create a very special clock path using the HSI48 with sync to USB frames (then programmer can not be used stand alone - a feature planned for future use, just like WRITER).

Also, since you changed the opamp, it might be possible that the output voltages differ. You can use the "easypdkprogtest" program to check that the output voltage is correct:

DO THIS WITHOUT A MCU CONNECTED TO THE PROGRAMMER

make easypdkprogtest

./easypdkprogtest
vdd: 5.01   vpp: 4.98    (vref= 3.30)


Please check that VDD and VPP are 5V and VREF is 3.3V. Also measure them on your PCB.

In case VDD and VPP voltages are incorrect you need to tune the DAC reference values for your specific hardware (in fpdk.c you need to change FPDK_VDD_DAC_MAX_MV / FPDK_VPP_DAC_MAX_MV).


JS

Where to get it "easypdkprogtest" program ? File Directory path . Thanks!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 12, 2019, 04:09:40 pm
The depdk converted bin file cannot be written to the target chip using easypdkprog Is there a way to convert the bin file to an ihx file ?

There is no way to "convert" a PDK file. PDK files contain extra code which the original WRITER device form PADAUK needs to modify during writing.
You can use SDCC (a real C compiler) to create wonderful programs.

Where to get it "easypdkprogtest" program ? File Directory path . Thanks!

The source code is inside of the github project (you need to compile it yourself) : https://github.com/free-pdk/easy-pdk-programmer-software


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 12, 2019, 04:31:04 pm
Hi,

I just released version 1.2 of the EasyPDK programmer software: https://github.com/free-pdk/easy-pdk-programmer-software/releases/tag/1.2


The following features are fully implemented now:

FUSES: Setup fuses from SDCC source code
SYSCLOCK IHRC: Tuning (500kHz - 8MHz, overclocking up to 11MHz possible)
SYSCLOCK ILRC: Tuning (3-100kHz)
BANDGAP: BG tuning (1.2V)

There is example code for FUSES and calibrations in "calib-and-fuse-demo.c".


I think it is now feature complete for PMS150C, PFS154 and PFS173. Next steps: adding new IC types.


=> DON'T FORGET TO UPDATE THE PROGRAMMER FIRMWARE <=

Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 12, 2019, 10:07:10 pm
Big thumbs up JS, Please add the industrial grade parts with ADC as the first Step :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on December 13, 2019, 07:38:01 am
(https://image.easyeda.com/pullimage/0saC7lN9uPN13wP1Y6bCfeq7nIJxO12LutiRiZsv.png)
What does RO mean in brackets on the right of the list?


(https://image.easyeda.com/pullimage/Ft4rV3Wg1mUXuZBBCFR5T3GNhflo3rakKVfoBwu5.png)
Thanks JS ! version 1.2 verygood !
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 14, 2019, 03:19:29 pm
JS please add PMC131 and PMC271 parts support, they are industrial grade and have ADC
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 14, 2019, 05:54:49 pm
JS please add PMC131 and PMC271 parts support, they are industrial grade and have ADC

I suggest to file feature requests for those two at GitHub:

https://github.com/free-pdk/easy-pdk-programmer-software/issues
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on December 15, 2019, 09:45:09 am
I used to be on this topic downloaded a command line utility  that can parse the PDK file , and it can show which IC types  the PDK file was compiled . But now I can't find that command line utility through this topic. Do you help me find it ?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 16, 2019, 04:56:58 pm
(https://image.easyeda.com/pullimage/0saC7lN9uPN13wP1Y6bCfeq7nIJxO12LutiRiZsv.png)
What does RO mean in brackets on the right of the list?

RO stands for Read-Only - which means writing the IC is not fully implemented / tested yet.


I used to be on this topic downloaded a command line utility  that can parse the PDK file , and it can show which IC types  the PDK file was compiled . But now I can't find that command line utility through this topic. Do you help me find it ?

The decryption tool is on page 2 of this thread, post #28:  https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1946371/#msg1946371 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg1946371/#msg1946371)

This (experimental) tools are also included in the FREEPDK github repository: https://github.com/free-pdk (https://github.com/free-pdk)  ==> fppa-pdk-tools
  => depdk.c (decryption tool)
  => dispdk.c (disassembler, can open PDK file directly and outputs which CPU was used and disassembly)

This are experimental tools, used during devlopment only. They do not and will not support all IC types and all flavors of PDK files.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 16, 2019, 05:05:07 pm
JS please add PMC131 and PMC271 parts support, they are industrial grade and have ADC

Hi, PMS and PMC variants are 100% identical regarding compiler and programmer.

Do you have a specific project you might share, which is intended to run on a PMC part with ADC? By sharing a project the motivation to support a specific IC type would increase a lot  :).

Personally I found that PFS173 is by far the best option for almost everything. It has big FLASH, ADC, 256 byte RAM and they are available as SOT23-6, SOP8, SOP14, SOP16, ... as cheap as USD 0.05 (https://item.taobao.com/item.htm?id=598420620199 ) or USD 0.07 (https://lcsc.com/product-detail/Others_PADAUK-Tech-PFS173-S08_C337970.html)

Have fun,

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 17, 2019, 06:14:07 am
Thanks JS, I find the PFS173 to be very useful, I need it to capture some Signals with ADC and send them over uart! The only problem with PFS173 is the working temperature! it's not -40 to 85C, so It can not be used inside industrial gears, Also the SOT23-6 package is very nice to have. then unfortunately we do not have something in the -40 to 85c in the PMC parts :palm:

If the PFS173 temperature range was industrial, then we where in heaven :)
I think these babies can be used in very low cost PLC ADC modules ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 17, 2019, 07:56:18 am
Thanks JS, I find the PFS173 to be very useful, I need it to capture some Signals with ADC and send them over uart! The only problem with PFS173 is the working temperature! it's not -40 to 85C, so It can not be used inside industrial gears, Also the SOT23-6 package is very nice to have. then unfortunately we do not have something in the -40 to 85c in the PMC parts :palm:

You mean "in the PFS parts", I guess. The PMC and PFC parts are -40°C to +85°C.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 18, 2019, 12:59:23 pm
why PFS173 would not boot properly when connected to an external 5V supply to work as stand alone? :palm:
should be reset pulled up to VCC? I have done it and got no luck!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 19, 2019, 04:10:52 pm
why PFS173 would not boot properly when connected to an external 5V supply to work as stand alone? :palm:
should be reset pulled up to VCC? I have done it and got no luck!

You do not have to connect RESET pin to anywhere. The RESET pin is only used in case YOUR program sets up PRSTB bit in CLKMD register.

In case your program is not running after flashing this can have several causes:
- check that you disabled watchdog, or when enabled that you call WDRESET periodically
- check that you disabled LVR or that you set LVR to a level greater or equal to VCC
- make sure your CLKMD setup (e.g. switching from ILRC to IHRC does not disable the old clock source immediately (see note in PFS173 PDF about clock switching).

If you can't work it out yourself, posting your program source code would enable others to have a look.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 20, 2019, 11:25:42 am
There will be a short talk on the free toolchain for the Padauk µC on 12:00 Sunday the 2nd of February at FOSDEM 2020:

https://fosdem.org/2020/schedule/event/paduak_toolchain/

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 21, 2019, 06:46:53 am
Dear JS, It's now solved! the problem was the FTDI chip that was making some power into the chip when it was not powerd!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 10, 2020, 12:25:32 am
There will be a short talk on the free toolchain for the Padauk µC on 12:00 Sunday the 2nd of February at FOSDEM 2020:

https://fosdem.org/2020/schedule/event/paduak_toolchain/

Nice! Will the talk be recorded? Or will at least the slides be available?

Btw, where do you get the €0.01 from? Haven't seen an update at LCSC for a long time. I am still waiting for the PFS232 to become available.

I have designed a tiny new project with the PFS154. Will assemble and write it up in about two weeks when the parts arrive.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 10, 2020, 12:21:44 pm
There will be a short talk on the free toolchain for the Padauk µC on 12:00 Sunday the 2nd of February at FOSDEM 2020:

https://fosdem.org/2020/schedule/event/paduak_toolchain/

Nice! Will the talk be recorded? Or will at least the slides be available?

Slides will become available  a few hour before the talk. FOSDEM records all talks (https://video.fosdem.org/), but in the past I've sometimes experienced technical problems (e.g. distortion and the leftmost part of my slides missing in the recording of one of my FOSDEM 2018 talks https://ftp.fau.de/fosdem/2018/UD2.218A/stm8.mp4).

Quote

Btw, where do you get the €0.01 from?

I've seen that price for the PMS15A (at a minimum order of 10) at various places.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: alvieboy on January 22, 2020, 03:14:49 pm
Hi all,

I am working on a interrupt-based, timing sensitive project to be implemented on a PFS154 controller. For this project I needed very fast interrupt response, and I needed to evaluate if the interrupt processing, which include pin sampling, could sustain the expected interrupt rate.

This was not easy to test using software, so I wrote a VHDL simulation model for PDK14 (PFS154).  The model should work with any HDL VHDL simulation engine, such as GHDL or Modelsim.

Not every PDK14 opcodes are implemented as of now, but should be fairly easy to implement the missing ones. I have also a PDK15 implementation but it's currently lagging behind.

The simulation model includes GPIO, basic T16 support, Timer2 and Timer3, and PWMG0. It should support all the clock sources for sysclk and for the timers.

You can find the VHDL model here:

https://github.com/free-pdk/fppa-pdk-emulator-vhdl

There is a basic example inside "examples/test" you can run. See the README file inside that folder for details.

I sincerly hope this can be useful to anyone as it is for me. Let me know if you find any issues, or have any feature request.

Best,
Alvaro Lopes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 22, 2020, 06:17:18 pm
I saw it today. Looks like massive work! Is it synthesizable? This could be the foundation for an open-source in-circuit emulator based on any cheap FPGA board. It would ease development for the OTP variants a lot.

I wonder, what is so peculiar about the PFS154 interrupts? Since every instruction is executed in one or two cycles, the interrupts should be fairly quick and with low jitter?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: alvieboy on January 22, 2020, 08:40:18 pm
I saw it today. Looks like massive work! Is it synthesizable? This could be the foundation for an open-source in-circuit emulator based on any cheap FPGA board. It would ease development for the OTP variants a lot.
As of now, it is not synthesizable. Mainly because there are a few open questions regading the microcontroller implementation (see the toplevel README, I have a few questions there that need to be answered).
Quote
I wonder, what is so peculiar about the PFS154 interrupts? Since every instruction is executed in one or two cycles, the interrupts should be fairly quick and with low jitter?
They are quick... but it's hard to understand if you can keep up the pace when the interrupt sources come at only a few microsseconds apart. Simulating this at a lower level allows you to test several scenarios and evaluate whether your design will work or not. What I can tell you is, my first version which was implemented in "C" and built with SDCC was *not* able to keep pace. I found this during simulation, and simulation helped me optimize the (now in assembly) code.

There is something peculiar about how SDCC generates the interrupt handler, though. I ended up with the following sequence which was non-optimal (in addition to the goto statement due to memory location, I presume)

pushaf
mov a, p
pushaf
// Interrupt code
popaf
mov p, a
popaf
reti

I did not require modification of A for the most important part of the interrupt routine. And definitely not using "p". 6 less instructions to execute, 750ns saved. Quite important when you have 3 us between interrupts, and you need to serve them quickly because you need to sample pins from within the interrupt routine.

Alvaro
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 23, 2020, 01:40:14 pm
I saw it today. Looks like massive work! Is it synthesizable? This could be the foundation for an open-source in-circuit emulator based on any cheap FPGA board. It would ease development for the OTP variants a lot.
As of now, it is not synthesizable. Mainly because there are a few open questions regading the microcontroller implementation (see the toplevel README, I have a few questions there that need to be answered).
Quote
I wonder, what is so peculiar about the PFS154 interrupts? Since every instruction is executed in one or two cycles, the interrupts should be fairly quick and with low jitter?
They are quick... but it's hard to understand if you can keep up the pace when the interrupt sources come at only a few microsseconds apart. Simulating this at a lower level allows you to test several scenarios and evaluate whether your design will work or not. What I can tell you is, my first version which was implemented in "C" and built with SDCC was *not* able to keep pace. I found this during simulation, and simulation helped me optimize the (now in assembly) code.

There is something peculiar about how SDCC generates the interrupt handler, though. I ended up with the following sequence which was non-optimal (in addition to the goto statement due to memory location, I presume)

pushaf
mov a, p
pushaf
// Interrupt code
popaf
mov p, a
popaf
reti

I did not require modification of A for the most important part of the interrupt routine. And definitely not using "p". 6 less instructions to execute, 750ns saved. Quite important when you have 3 us between interrupts, and you need to serve them quickly because you need to sample pins from within the interrupt routine.

Alvaro

You also can get rid of the 2 extra cycles from the GOTO statement in case you manually instruct SDCC to place your interrupt code directly to the right position.

Here my example code how to setup a naked interrupt (without pushf/popf) which places the code at int vector location directly:

void naked_interrupt(void) __naked
{
  __asm
      .area NAKEDINT (ABS)   ;place following code in a new segment 'NAKEDINT' with absolute positioning '(ABS)'
      .org  0x0020           ;set position to 0x0010  (multiplied by 2 since SDCC expects byte pos here)

      ;Interrupt code        ;your interrupt code which takes care of A, flags and virtual 'p' register (RAM location of 1 word @0x0000)
      nop
      nop
      nop

      reti                   ;last instruction must be 'reti' to return from interrupt

      .area CODE             ;switch back to normal segment 'CODE' for following code
  __endasm;
}


EDIT: To make it work I needed to place the naked interrupt in an extra file which needs to be given to the linker before the file which contains main. Then there was still a problem since SDCC PDK compiler always creates code for an interrupt vector when it finds the main() function in a source file.

So following code will work:

nakedint.c
void naked_interrupt(void) __naked
{
  __asm
      .area   HEADER(ABS)      ;place following code in the segment 'HEADER' with absolute positioning '(ABS)'
      .org  0x0020             ;set position to 0x0010  (multiplied by 2 since SDCC expects byte pos here)
      .org  0x0020             ;3 times .org seems to confuse SDCC so it will place later HEADER section with int vector @0x000F
      .org  0x0020             ;this seems to be a bug in SDCC but I did not find any other way to avoid SDCC PDK compiler to place the interrupt vector
      nop                      ;this dummy instruction is located at 0x000F and will be overwritten later from SDCC interrupt vector placement (will become 'reti')

      .area   HOME             ;we place code in 'HOME' area which now begins @0x0010 (the correct interrupt vector location)

      ;Interrupt code          ;your interrupt code which takes care of A, flags and virtual 'p' register (RAM location of 1 word @0x0000)
      nop
      nop
      nop

      reti                     ;last instruction must be 'reti' to return from interrupt
  __endasm;
}


main.c

unsigned char _sdcc_external_startup(void)
{
  return 0;
}

void main(void)
{
  for( ;; );
}



commands to compile:
sdcc -mpdk14 -c nakedint.c -o nakedint.rel
sdcc -mpdk14 -c main.c -o main.rel
sdcc -mpdk14 nakedint.rel main.rel -o testnakedint.ihx


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: alvieboy on February 01, 2020, 04:18:58 pm
Restrictions on INTEGS bit manipulation

All,
Is anyone aware of any restriction for bit manipulating INTEGS ?

Let me tell you what I am experiencing. Part is PFS154-S16.

I have a complex interrupt routine that triggers on PA0 edges, but the edge detection changes due to the nature of the algorithm I am using.
For this particular part of the interrupt, PA0 rising edge is being used, PB0 also used as both edges, and T16 is also used as rising edge. This gives a INTEGS value of 0b000_0_00_01., i.e., all bits are zero except for bit 0 (selecting [1:0] as "01" as required for rising edge interrupt).

At some point in the algorithm I need to enable both edges interrupt on PA0, and I need to do this from the interrupt routine (and when processing an PA0 interrupt - also the interrupt is acked immediatly at ISR entrance). For that purpose I manipulate only the bit0 of INTEGS, setting it to '0' to select both edge interrupt. This is done in assembly using:

        set0 _integs, #0  // Activate interrupt on both edges

So far so good, I can see the interruptions coming in when edge changes, either rising or falling.

Now, at another point in the algorithm I need to re-enable only rising edge interrupts (also from within the interrupt routine, and while processing PA0 falling edge interrupt). But when I do this:

        set1 _integs, #0  // Activate interrupt on rising edge only

I lose both rising and falling interrupts. I see interrupts from other sources coming in, but never from PA0.

After some experimentation, I found out that this below does work, though:

        mov a, #1
        mov _integs, a  // Activate interrupt on rising edge only

So this leads me to believe that there are some restrictions regarding bit manipulation of INTEGS register.

Does anyone have any insight on this ?

Best,
Alvaro
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 02, 2020, 01:00:32 pm
Hi,

Have you set the other bit to 0 before (e.g.  set0 _integs, #1)?

Have you tried to read back the value after using set1 ?

Or.... To setup PA / PB in INTEGS register 2 bits are required to set F/R/B. Maybe the logic inside of the PADAUK CPU is not working correct when changing only one bit out of the 2 bit value.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on February 15, 2020, 02:47:29 pm
Hi again.
I have 2 questions.

1. I can't read input when PADIER = 0. Tested with PFS154.
Is there some kind of bug, or I'm missing something in the documentation?
Code: [Select]
__sfr __at(0x03) clkmd;
__sfr __at(0x0d) padier;
__sfr __at(0x0e) pbdier;
__sfr __at(0x10) pa;
__sfr __at(0x11) pac;
__sfr __at(0x12) paph;

unsigned char _sdcc_external_startup(void){
return 0;
}

void main(void){
paph = (1<<5); // Enable pull-high
pa   = 0; // HI
pac  = (1<<0); // Enable output
padier = 0;//(1<<5); // Enable PA5 wake up event

while(1){
if((pa&(1<<5))) pa |= (1<<0);
else pa &= ~(1<<0);
}
}

2. I got strange 2x speed difference between PFS154 and PMS150C.
Both set to 0x80 in IHRCR. PMS150C is 2 times slower (pwm speed and instruction execution time).
I need to set IHRCR really high (0xDA) to get the same results. Is it normal?
Is there a IHRCR factory calibration value for PMS150C in memory?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 17, 2020, 10:38:45 am
Hi again.
I have 2 questions.

1. I can't read input when PADIER = 0. Tested with PFS154.
Is there some kind of bug, or I'm missing something in the documentation?

No bug. Just like it is. If you want to use a pin as digital input you have to enable the digital input pin in PxDIER = "Port x Digital Input Enable Register".

On PFS154 default value after reset is 0xFF (all pins input), on PFS173 default value is 0 (no pins input).
So any application using a digital pin as input should always set PxDIER for this pin.

2. I got strange 2x speed difference between PFS154 and PMS150C.
Both set to 0x80 in IHRCR. PMS150C is 2 times slower (pwm speed and instruction execution time).
I need to set IHRCR really high (0xDA) to get the same results. Is it normal?
Is there a IHRCR factory calibration value for PMS150C in memory?
Also nothing strange here. This is just how the ICs are manufactured (big variance from batch to batch from IC to IC).
Most production lots of PMS150C I bought need a much higher value in IHRCR than PFS154.
Only the flash based ICs (PFSxxx) do have a factory calibration value for IHRCR (@16MHz, @5.0V, @20°C).

Since variation of ICs is so big you always should include a tuning procedure after writing.
EasyPDK programmer and PADAUK_WRITER both support IHRCR calibration. You can find code examples how to use calibration inside of the release of EasyPDK programmer.


Have fun,

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on February 17, 2020, 11:43:10 am
No bug. Just like it is. If you want to use a pin as digital input you have to enable the digital input pin in PxDIER = "Port x Digital Input Enable Register".
Thank you for answer.
I thought PxC register is input/output switch and PxDIER is for wake up enable. There is nothing about input in bit definitions.

"Enable PA7~PA3 wake up event. 1 / 0 : enable / disable.
These bits can be set to low to disable wake up from PA7~PA3 toggling."

There is also nothing about it in "IO Pins" chapter.

"...all the pins can be independently set into two states output or input by configuring the data
registers (pa), control registers (pac) and pull-high registers (paph)......
If user wants to read the pin state, please notice that it should be set to input mode before
reading the data port....
When PMS15A/PMS150C is put in power-down or power-save mode, every pin can be
used to wake-up system by toggling its state. Therefore, those pins needed to wake-up system must be set to
input mode and set the corresponding bits of registers padier to high."

Only after analyzing "Hardware diagram of IO buffer", the reader may state that the description is incorrect.
The behavior of the chip also does not match the mentioned diagram. Read is always HI when PxDIER is LOW. If there is an AND gate, the read should be LOW.
Padauk put this AND gate in wrong place. It's a bug.

Also nothing strange here. This is just how the ICs are manufactured (big variance from batch to batch from IC to IC).

Exactly 2x speed difference looked too suspicious, so I asked.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 17, 2020, 02:16:49 pm
No bug. Just like it is. If you want to use a pin as digital input you have to enable the digital input pin in PxDIER = "Port x Digital Input Enable Register".
Thank you for answer.
I thought PxC register is input/output switch and PxDIER is for wake up enable. There is nothing about input in bit definitions.

"Enable PA7~PA3 wake up event. 1 / 0 : enable / disable.
These bits can be set to low to disable wake up from PA7~PA3 toggling."

There is also nothing about it in "IO Pins" chapter.

"...all the pins can be independently set into two states output or input by configuring the data
registers (pa), control registers (pac) and pull-high registers (paph)......
If user wants to read the pin state, please notice that it should be set to input mode before
reading the data port....
When PMS15A/PMS150C is put in power-down or power-save mode, every pin can be
used to wake-up system by toggling its state. Therefore, those pins needed to wake-up system must be set to
input mode and set the corresponding bits of registers padier to high."

Only after analyzing "Hardware diagram of IO buffer", the reader may state that the description is incorrect.
The behavior of the chip also does not match the mentioned diagram. Read is always HI when PxDIER is LOW. If there is an AND gate, the read should be LOW.
Padauk put this AND gate in wrong place. It's a bug.

I also learned it the hard way... spending a lot of time why PFS173 input pin sampling was not working... which was caused by default reset value of 0x00 in PxDIER on PFS173 vs. 0xFF on all other ICs I tried before (e.g. PMS150C/PFS154/PMS154B/...). PADAUK "fixes" this in their always inserted init code (MOV A, 0xFF , MOV PADIER, A) on PFS173.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gaganchd2000 on February 20, 2020, 02:37:49 am
Hi
I am using PMS171B chip which Has ADC. I want to read the analog on one of the pins. first I tried to use Code generator feature of the IDE. On compilation I get this error.   "ADCC can't be 0x80 (Enable, 0x0:??)"

Expert can you please help and let me know what is the reason for error.
here is the standard code generated by IDE.


      // 1   :   All Assembly
      mov      A, 80h;
      mov      ADCC, A;         //   $ ADCC   Enable, PB0;  ( error is here)
      set1   AD_Start;
      .wait1   AD_Done;
      mov      a, ADCR;
      mov      buf[0], a;

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on February 22, 2020, 08:28:43 pm
Thanks for the code. I seem to have an endianess problem somewhere.
I am using linux, but the IDE doesnt work with wine.
So I used windows to make and convert the file. Somehow bytes got swapped  :palm:

Just to mention that I installed Padauk's FPPA IDE 0.88 under Wine 3.7 on openSUSE Leap 15.1 and so far what I tested seems to work. I cloned Jay Carlson's bike light project from his Github repo and built it and it generated OBJ files. Or course when I tried to debug the program it couldn't find an ICE. I also ran Writer.exe and it started but it couldn't find a programmer on USB.

I hope this helps someone in case they need a working Padauk IDE on Linux to experiment with or whatever.

I don't actually have any Padauk MCUs, ICE, or programmer, I'm just playing around. Waiting for some module manufacturer like Elecrow to make and sell the open source Easy PDK programmer .

Sounds exciting. Great work, guys.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gaganchd2000 on February 24, 2020, 09:32:59 pm
Finally fix the issue myself. Was configuring incompatible values.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on February 26, 2020, 06:16:43 pm
There is an article on Digitimes about our favourite MCU manufacturer:

https://www.digitimes.com/news/a20200225PD209.html (https://www.digitimes.com/news/a20200225PD209.html)

Quote
Taiwan-based MCU maker Padauk Technology expects its shipments of MCU products to grow by over 20% on year to reach 1.3 billion units in 2020, according to company Tang Tsan-bih.

Despite growing concerns about the stability of related supply chain caused by the coronavirus outbreak, Tang said that he believes demand for MCUs will remain strong, particularly from sectors including 5G base stations, servers and other cooling fan systems.

Boasting a group of strong supply chain partners, including Magnachip Semiconductor and Powerchip Semiconductor Manufacturing (PSMC) for wafer foundry and Greatek Electronics for IC backend services as well as inventories of needed components for up to three months, Padauk is readied to support product roll-outs of its clients, Tang stated.

For individual product category, shipments of 8-bit MCUs for BLDC (brushless DC) motors will account for about 30% of its totals sales in 2020, up from 23% a year earlier, Tang revealed.

Meanwhile, the company is also expected to see its shipments of MCUs for TWS (true wireless stereo) devices expand significantly in 2020, having shipped about 20 million units to the sector in 2019, according to an estimate of industry sources.

The sources also estimated that Padauk will see its 2020 revenues grow over 10% from the NT$522 million (US$17.17 million) it recorded a year ago.

Shares of the MCU maker is scheduled to debut on Taiwan's OTC securities market in the second half of March.

So they sell 1.3 billion units on 17.17 million revenue. That means their average selling price is just $0.013 USD! They must sell plenty of $0.01 USD microcontrollers... Also, 10% YoY ASP erosion. These guys are playing with fire - exactly the opposite of what every other company would do.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on March 07, 2020, 02:06:41 pm
Is anyone selling JS' programmer yet? I'd also be happy to buy a one-off made one (used too, as long as it's working) from any of you people.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on March 18, 2020, 12:06:32 pm
JS, I want to know how we enable options in the SDSC, for example in the PFS173 Datasheet there are these options regarding clocking tim2 and Comparator usage,

GPC_PWM which can Enable Comparator controls all PWM outputs, and TMx_Source  When tm2c[7:4]= 0010, TM2 clock source = IHRC*2 = 32MHZ and PWM_Source  When Pwmgclk.0= 1, PWMG clock source = IHRC*2 = 32MHZ

There are these defines in the pfs173.h

Quote
#define ROP_TMX_6BIT                   0x00
#define ROP_TMX_7BIT                   0x10
#define ROP_TMX_16MHZ                  0x00
#define ROP_TMX_32MHZ                  0x20
#define ROP_PURE_PWM                   0x00
#define ROP_GPC_PWM                    0x40
#define ROP_PWM_16MHZ                  0x00
#define ROP_PWM_32MHZ                  0x80

how we should use them? I want to change the TIM2 clock to 32MHz and use the Comparator  to control the PWM.

Take a look at this picture from the PFS173 Datasheet

Thanks

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 20, 2020, 08:37:49 am
JS, I want to know how we enable options in the SDSC, for example in the PFS173 Datasheet there are these options regarding clocking tim2 and Comparator usage,

GPC_PWM which can Enable Comparator controls all PWM outputs, and TMx_Source  When tm2c[7:4]= 0010, TM2 clock source = IHRC*2 = 32MHZ and PWM_Source  When Pwmgclk.0= 1, PWMG clock source = IHRC*2 = 32MHZ

There are these defines in the pfs173.h

Quote
#define ROP_TMX_6BIT                   0x00
#define ROP_TMX_7BIT                   0x10
#define ROP_TMX_16MHZ                  0x00
#define ROP_TMX_32MHZ                  0x20
#define ROP_PURE_PWM                   0x00
#define ROP_GPC_PWM                    0x40
#define ROP_PWM_16MHZ                  0x00
#define ROP_PWM_32MHZ                  0x80

how we should use them? I want to change the TIM2 clock to 32MHz and use the Comparator  to control the PWM.

Take a look at this picture from the PFS173 Datasheet

Thanks

Hi,

The defines in the .h files for the ICs always begin with the SFR name.
In order to set the "options" (this is just a marketing name from Padauk, in fact these are values in ROP SFR and other SFRs) you just assign them to the SFR like this:

unsigned char _sdcc_external_startup(void)
{
  //setup + tune your SYSCLK (e.g. EASY_PDK_INIT_SYSCLOCK_8MHZ(); EASY_PDK_USE_FACTORY_IHRCR_16MHZ(); )

  //set ROP values
  ROP =  ROP_TMX_7BIT | ROP_GPC_PWM | ROP_TMX_32MHZ | ROP_PWM_32MHZ;

  return 0;
}


As you can see you can not set TM2 and TM3 differently => TMX is used to reflect this.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on March 20, 2020, 09:55:46 am
Thanks JS, I want to do a simple buck controller with these options, have you done any DC/DC converter with these padauk MCUs?
Also there is nothing mentioning ROP register in the Datasheet, how did you find it?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 21, 2020, 04:04:31 pm
Thanks JS, I want to do a simple buck controller with these options, have you done any DC/DC converter with these padauk MCUs?
Sorry, I never made a DC-DC myself, I always used dedicated ICs for this purpose.

Also there is nothing mentioning ROP register in the Datasheet, how did you find it?
The .h files from the original PADAUK IDE contain all this information :)
Have a look at: "C:\PADAUK_Tool\0.88\INC_PDK\PFS173.INC" :
...
.Assembly   OPTION_ROP   1   Interrupt_Src0   PA.0   PB.5
.Assembly   OPTION_ROP   0   Interrupt_Src1   PB.0   PA.4
.Assembly   OPTION_ROP   6   GPC_PWM         Disable   Enable
.Assembly   OPTION_ROP   7   PWM_Source   16MHz   32MHz
.Assembly   OPTION_ROP   5   TMx_Source   16MHz   32MHz
.Assembly   OPTION_ROP   4   TMx_Bit      6BIT   7BIT
...
   ROP      IO_WO:OP      0x67 (0x2A)
      $ 7   :   PWM_16MHz, PWM_32MHz
      $ 6   :   PURE_PWM, GPC_PWM
      $ 5   :   TMx_16MHz, TMx_32MHz
      $ 4   :   TMx_6BIT, TMx_7BIT
      $ 1   :   PA0, PB5
      $ 0   :   PB0, PA4
...


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on April 05, 2020, 12:08:28 pm
I finally got around documenting my last project with the Padauk MCU. It's a chainable 7 segment disaply, where each segment is controlled by PFS154.

It's not too exciting, but I thought it was a suitable application for a 3 cent MCU and is a nice testbed to play around with networking protocols.

You can find a writeup here: https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/ (https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/)

Btw, one nice trick I found during the design was to use a SOIC8-clamp for programming (see attachment). All Padauk MCU have their supply and programming pins arranged in a way that easily allows doing this. No need to add any ISP connectors. You can get these very cheap on aliexpress and ebay.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on April 05, 2020, 04:16:16 pm
You also can get rid of the 2 extra cycles from the GOTO statement in case you manually instruct SDCC to place your interrupt code directly to the right position.

Since the Padauk all only have a single interrupt, and none all seem to have user program immediately after it, this should always work.

So I opened a feature request for SDCC:

https://sourceforge.net/p/sdcc/feature-requests/673/

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 12, 2020, 03:58:06 am
A quick dumb question. Will EasyPDK computer side software work with official padauk programmer? Or do I have to build an EasyPDK programmer hardware?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: zitt on April 12, 2020, 07:33:33 am
Hoping one of you Padauk experts can help me "get started" with these tool sets:
https://www.eevblog.com/forum/microcontrollers/padauk-pfs154-getting-started/ (https://www.eevblog.com/forum/microcontrollers/padauk-pfs154-getting-started/)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 14, 2020, 08:31:14 am
Hello LovelyA72 and zitt,

both of your questions are related to the possibility of mixing the free and open Free-PDK stuff (SDCC + EasyPDK programmer) with the legacy (closed/missing internal documentation) manufacturer tools (PADAUK IDE / WRITER / ICE).

A lot of work has been done to liberate the PADAUK ICs, so a free open source compiler (SDCC) supports it and a cheap to build programmer (EasyPDK programmer) is available now.

The focus was and is on adding better support to the free and open stuff, so not much effort on supporting the legacy manufacturer tools.


I feel your pain not to have a debugger. But there is just no way to connect both worlds right now.

Converting .ihex to .PDK and .PDK to .ihex is not difficult at all. The problem is that the PADAUK IDE compiler inserts a lot (>150 instructions) of invisible magic code at the start which is used to tune the IC during writing. The original WRITER then implements special procedures to do the tuning and altering the firmware based on the result for every single IC written. So when you convert from .ihex to .PDK you will not have the massive PADAUK tuning code (>150 instructions) inside of the firmware (EasyPDK requires just 10-12 instructions for the tuning procedure). This will result in untuned ICs which means instead of 8MHz system clock you end up with something between 5 - 10 MHz (different for every IC you write). Such a massive variation in system clock will cause problems in your program which might use a timer for serial output or something else. The conversion from .PDK to .ihex has the problem that the inserted startup code from PADAUK IDE must be found, disabled and replaced by a EasyPDK tuning procedure. This is possible, but the big amount of different startup code inserted from PADAUK IDE (which also changes from IDE version to version) makes identification + replacement a labor intense task with not much benefit.

There is a project from alvieboy which implements a PFS154 in VHDL. This might be the foundation for a FPGA based hardware emulator in the future. Right now it is for software simulation only.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 15, 2020, 04:31:03 am
Thank you for your detailed explanation! The major issue that I am having is that it is extremely difficult to obtain an EasyPDK programmer. STM32F072C8T6(and some other parts) becomes out of stock on LCSC for a long time(it means no jlcpcb SMT assembly). Also I found that assemble this programmer is really hard for people that lacks SMT soldering experience.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 15, 2020, 10:36:38 am
Thank you for your detailed explanation! The major issue that I am having is that it is extremely difficult to obtain an EasyPDK programmer. STM32F072C8T6(and some other parts) becomes out of stock on LCSC for a long time(it means no jlcpcb SMT assembly). Also I found that assemble this programmer is really hard for people that lacks SMT soldering experience.

In case the STM32F072  C8T6 version is not available you also can use the CBT6 version (STM32F072CBT6).
Basically it is the same processor which just has more flash memory (In reality there is the same silicon inside as in the "smaller" variant).

The resistors and capacitors can be replaced with any other offering, just make sure value (... Ohm /...k / ...nF / ...uF) and size (0603/1206/...) match.

The coil HPC3015TF-6R8M could be replaced by this one: CMLW3015S6R8MST.


I already used bigger SMT components (0603) to make hand assembly easier (I did over 50 pcs already). 0603 components can be soldered with small soldering tip and without a microscope.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: true on April 15, 2020, 02:02:27 pm
I'm busy on other projects now, but have the supplies and can supply my own version of the programmer in a few months (maybe August). That is, if you aren't in a hurry...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 20, 2020, 03:39:30 am
I am also having some questions related to the IDE. Is there a FreePDK IDE available? If not, is there any tool recommended to work with the SDCC compiler(like WinAVR can work with Programmer's Notepad)?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on April 20, 2020, 03:01:24 pm
The Code::Blocks (http://www.codeblocks.org/) IDE works quite well with SDCC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 20, 2020, 04:27:29 pm
Thanks for your advice! I ended up using Programmer's Notepad. I configured pn to work with SDCC and it works really nice. The best thing about pn is that it's portable. I can put pn and sdcc on a thumb drive and use it anywhere I want.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 10, 2020, 06:53:22 pm
Hi,

did anybody investigate how the LVR (low voltage reset) fuses for the PFS154 work?

I tried to manually set the fuse for example to 0x36E1, which should set the LVR to 4V. At least according to https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt (https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt).

But the PFS154 powers on right at about 2V and powers off again if I go below 2V. I do not disable the LVR in the MISC register, so I think it should not switch on fully before Vdd reaches about 4V.

I read back the fuse value with the read command and it was indeed set to 0x36E1 as expected.

Or do I misunderstand how the LVR function works?

Thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 11, 2020, 03:04:27 pm
Hi,

did anybody investigate how the LVR (low voltage reset) fuses for the PFS154 work?

I tried to manually set the fuse for example to 0x36E1, which should set the LVR to 4V. At least according to https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt (https://github.com/free-pdk/fppa-pdk-documentation/blob/master/Reserved_Area_Last_8_Words_Of_Codemem.txt).

But the PFS154 powers on right at about 2V and powers off again if I go below 2V. I do not disable the LVR in the MISC register, so I think it should not switch on fully before Vdd reaches about 4V.

I read back the fuse value with the read command and it was indeed set to 0x36E1 as expected.

Or do I misunderstand how the LVR function works?

Thanks.

Hi,

the LVR value is not a fixed place in code memory on PFS154, you have to program a SFR instead. Original PDK initialization code uses a fixed position to get a value and sets the SFR based on this.

I defined the SFR register names and settings for PFS154 in pfs154.h (see dev branch: https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/easypdk/pfs154.h )

Special Function Register (SFR) name is:

MISCLVR

Values are:

//misc_lvr definitions
#define MISCLVR_4V                   0x00
#define MISCLVR_3V5                  0x20
#define MISCLVR_3V                   0x40
#define MISCLVR_2V75                 0x60
#define MISCLVR_2V5                  0x80
#define MISCLVR_1V8                  0xA0
#define MISCLVR_2V2                  0xC0
#define MISCLVR_2V                   0xE0


So in order to setup 2V LVR you have to set (a good place for this is inside of _sdcc_external_startup() ):

MISCLVR = MISCLVR_2V;

Also make sure that you do not disable MISC_LVR in MISC register via MISC_LVR_DISABLE. The following line will disable MISC_LVR_DISABLE ... which means it is enabled.

MISC &= ~MISC_LVR_DISABLE;

Have fun,

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 11, 2020, 07:13:46 pm
Hi,

the LVR value is not a fixed place in code memory on PFS154, you have to program a SFR instead. Original PDK initialization code uses a fixed position to get a value and sets the SFR based on this.

I defined the SFR register names and settings for PFS154 in pfs154.h (see dev branch: https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/easypdk/pfs154.h )

Special Function Register (SFR) name is:

MISCLVR
aha, so on the PFS154 they aren't using the fuse as on PMS150C, read out by hardware, to set LVR, but a regular, undocumented register you have to set in your initialization code.

I've now got it to work with the MISCLVR register. Thanks for your help.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 17, 2020, 07:14:20 am
I have been wondering whether there are ways to to make the EASYPDK-programmer a bit more accessible. Dave did a great series showing how to assemble it, but it also took him quite a while and he had issues with some small parts. (He made some things with the toolchain look way more complicated than they are, but that is probably a for another discussion)

Just some thoughts what could be done. The goal should be to reduce the total number of parts and use slightly larger ones, where possible. (e.g. 0805)

1) Maybe the programmer could be designed in a way to piggybag on a bluepill? This would remove the need to source the controller and solder the USB port. I have to admit that it is quite bodgy though... Alternatively one could switch to a more available, but slightly more expensive MCU, like the STM32F103. Does it have DFU mode? Another option: Switch to a low-cost 8051 based USB micro (WCH...). But porting the firmware will be painful...

[attachimg=1]

2) There is a charge pump that generates -2.4V for the OPAMPs that control the programming voltages. This is needed to allow full voltage swing down to GND to be actually able to turn the supply voltages off. I have checked the AR358 (LM358 clone) datasheet and the output voltage swing goes down to 30mV. While this is not super-clean, pulling VPP and VDD to 30mV should be sufficient to disable the device to be programmed. SO maybe this part could be skipped and the OPAMP be connected to ground? JS, did you try this and it failed?

[attachimg=2]

3) The step up converter comes with dual mosfet to disable power supply. The Step-up-converter itself has an enable pin that is tied tied to always active. Turning off the step-up converter using the enabled input would result in 5V on the 15V supply. However, the 15V supply is only used to feed the opamps. If using the opamps to pull VPP and VDD to ground, it would be acceptable for them to be supplied from 5V when the boost converter is inactive. I have to admit that this is not super robust, but it shold likely be fine as long as the MCU is controlling everything while the device to be programmed is connected. Thus, Q1, Q1, R7,C11,C19 could be removed? One may want to put in a filter to protect the rest of the circuit from noise, though.

4) The 3.3V Supply (RT9193) could also be removed if the bluepill is used.

Does it make sense? Anything to add?

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 17, 2020, 07:28:53 am
@#853: I'd be happy to whip up and contribute a C::B wizard for Padauk when the hardware stuff becomes available to me. I just did one for STM8 with SDCC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 17, 2020, 10:35:25 am
1) Maybe the programmer could be designed in a way to piggybag on a bluepill? This would remove the need to source the controller and solder the USB port.
The Bluepill has two big downsides:
1) it nowadays often comes with incompatible, cloned microcontrollers, see for example https://www.mikrocontroller.net/topic/488417 (https://www.mikrocontroller.net/topic/488417)
2) Even when genuine, it uses the STM32F103, see below

Alternatively one could switch to a more available, but slightly more expensive MCU, like the STM32F103. Does it have DFU mode? Another option: Switch to a low-cost 8051 based USB micro (WCH...). But porting the firmware will be painful...
The STM32F103 does not come with a USB-Bootloader. So you would have to flash one in first. You'd need a ST-Link or similar for that, which makes first bringup much more complicated than now where you just have to hold a button.

Also the STM32F103 does not have DACs, which are necessary for the programmer to function. One could emulate that with PWM and some opamps, but that would add complexity, not reduce it.

The same goes for lowcost 8051 solutions. Getting it to work there is a lot of work and in the end won't make it cheaper or easier to build.

2) There is a charge pump that generates -2.4V for the OPAMPs that control the programming voltages. This is needed to allow full voltage swing down to GND to be actually able to turn the supply voltages off. I have checked the AR358 (LM358 clone) datasheet and the output voltage swing goes down to 30mV. While this is not super-clean, pulling VPP and VDD to 30mV should be sufficient to disable the device to be programmed. SO maybe this part could be skipped and the OPAMP be connected to ground? JS, did you try this and it failed?
This could maybe be optimized, but I'm not sure if it is worth it. The charge pump circuit is really small and straight forward. What could be done though is replacing the two small diodes with one BAT54S in SOT23. That would make populating it easier.

3) The step up converter comes with dual mosfet to disable power supply. The Step-up-converter itself has an enable pin that is tied tied to always active. Turning off the step-up converter using the enabled input would result in 5V on the 15V supply. However, the 15V supply is only used to feed the opamps. If using the opamps to pull VPP and VDD to ground, it would be acceptable for them to be supplied from 5V when the boost converter is inactive. I have to admit that this is not super robust, but it shold likely be fine as long as the MCU is controlling everything while the device to be programmed is connected. Thus, Q1, Q1, R7,C11,C19 could be removed? One may want to put in a filter to protect the rest of the circuit from noise, though.
I think the current solution is much cleaner, because it prevents any small power glitches and similar during turnon when the STM32 is still starting up. The way it is now, the Padauk only gets powered when the STM32 is fully controlling things.

I like the design of the programmer as it is now, as it does what it should without unnecessary bells and whistles. The footprints and lack of silkscreen sometimes make it harder to build than necessary though. There is some work being done porting the layout to Kicad right now, see github pull requests. I think this is a good starting point for optimizations in these areas.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 17, 2020, 10:57:57 am
Quote
I think the current solution is much cleaner, because it prevents any small power glitches and similar during turnon when the STM32 is still starting up. The way it is now, the Padauk only gets powered when the STM32 is fully controlling things.

Actually the reference voltage inputs of the OPAMP are pulled to GND by R4 and R9, so that the voltage at VDD and VPP of the device will always be GND, unless the STM32 is fully in control. I don't think power gating the boost-converter is necessary.

Quote
I like the design of the programmer as it is now, as it does what it should without unnecessary bells and whistles. The footprints and lack of silkscreen sometimes make it harder to build than necessary though. There is some work being done porting the layout to Kicad right now, see github pull requests. I think this is a good starting point for optimizations in these areas.

I also have little incentive to change anything in the programmer, because I have two working ones and JS did a very good job with the programmer and the firmware. But saying that there is no need to lower the entry barrier by reducing the programmer complexity, where possible, may be ignoring the many people that have issues with building one. I was hoping to get some constructive discussion going.

Btw, I noted the STM32F072C8T6 is available at LCSC again.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 17, 2020, 11:12:07 am
Actually the reference voltage inputs of the OPAMP are pulled to GND by R4 and R9, so that the voltage at VDD and VPP of the device will always be GND, unless the STM32 is fully in control. I don't think power gating the boost-converter is necessary.
Ok, you are right. So one could get rid of Q1, Q2, R7 and enable the stepup from the STM32, keeping R26 as pulldown for the EN. The datasheet of the MT3608 defines EN input high as minimum 1.5V, so we are good with the 3.3V from the STM32.

C11 and C19 are necessary though, they are the input capacitors for the stepup, no reliable operation without them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 17, 2020, 11:39:27 am
Btw, I noticed that JS has optimized the BOM of the EASYPDKprog for lowerst cost at LCSC.

JLPCB has a slightly different catalogue for part they allow to use for their assembly service. All parts in the "Basic" category do not require any addional set up cost. So, if it was possible to build the easypdkprog only from parts in the basic category, it could be ordered fully assembled at reasonable cost.

https://jlcpcb.com/parts
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 17, 2020, 03:03:29 pm
Hi,

There are several things which could be stripped down to make e.g. a "LITE" version:

- remove LEDs
 (-3 leds, -3 resistors)
- remove push button (users could bridge two pads to enter DFU mode)
 (-1 push button)
- remove ADC input, this is not needed for normal operation, it's for a future feature, to be able to read out protected ICs by writing 0 bits and monitor power consumption, but not needed in LITE version
 (-4 resistors)
- remove of transistors for step up enable (as long as STM32 is not running, negative voltage is not generated for opamp. since the step up outputs the input voltage in case enable pin is low this will let some small voltage go directly to the socket)
 (-2 transistors, -1 resistor)
- remove negative opamp feed (diodes) - this might cause trouble during programing, but with all observations of already supported ICs an offset voltage on VDD to GND might be compensated with a higher programing voltage
 (-2 diodes, -2 capacitors)
- remove crystal (the crystal is there for high accurate tuning of IC after writing ... in case the LITE version is always attached to USB and will not have stand alone mode - planned future feature - then clock can be synced to USB to achieve good tuning result)
 (-1 crystal, -2 capacitors)
- use resistor array for connections to IC
 (-5 resistors, +1 array)

The main idea when creating the programmer over a year ago was to have a versatile platform which leaves room for improvements and testing new tricks which not been implemented / tested in this moment.

Personally I think it is to early to reduce the programmer. Maybe the ADC will be very handy in future? Maybe the 0 voltage output of the opamp is required for some ICs? Maybe the conservative way of completely disabling the output of the step up saved a lot of ICs since during STM32 startup/ USB connects / DFU updates / ... a lot of wired states been observed?

And since the target ICs will never be close to any "Arduino" experience, writing software for them is a much bigger challenge than to save a handful of components.

It would be more helpful to support adoption of new ICs and to create better introductions / walk throughs for beginners.

You saw Dave struggling when he tried his own "Hello World" (even that there are fully working and pre compiled examples including make files coming with the EasyPDK programmer software... He just overlooked this).

JS

EDIT: Direct link to EasyPDK code examples: https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples  <=============== CODE EXAMPLES
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 17, 2020, 05:31:21 pm
Btw, I noticed that JS has optimized the BOM of the EASYPDKprog for lowerst cost at LCSC.

JLPCB has a slightly different catalogue for part they allow to use for their assembly service. All parts in the "Basic" category do not require any addional set up cost. So, if it was possible to build the easypdkprog only from parts in the basic category, it could be ordered fully assembled at reasonable cost.
I like the idea of opitmizing the programmer so that it can be easily populated by the JLCPCB SMT service. Unfortunately the STM32F072C and the MT3608 are both "extended" parts, so I don't see any way around that additional setup fee without creating a substantially different programmer.

When using the SMT service for the first time, you usually get a coupon, which reduces the cost. So I don't think the price of the programmer is too much of an obstacle for widespread adoption.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 17, 2020, 07:38:38 pm
Hi JS,

thanks a lot for your insights.

- remove negative opamp feed (diodes) - this might cause trouble during programing, but with all observations of already supported ICs an offset voltage on VDD to GND might be compensated with a higher programing voltage
 (-2 diodes, -2 capacitors)

My understanding is that this will not generate an offset, but it will not allow VDD to go to 0V. Instead it will move to 20mV. To be honest, I don't think that is an issue since the main requirement is to pull VDD low enough for the POR circuit to perform a reset. 20mV should be more than sufficient. The datasheet says the POR limit is >1.8V.

It would be more helpful to support adoption of new ICs and to create better introductions / walk throughs for beginners.

You saw Dave struggling when he tried his own "Hello World" (even that there are fully working and pre compiled examples including make files coming with the EasyPDK programmer software... He just overlooked this).

Fully agree. To be really honest, we may need to solve the issue of having example code for four different environments first. (Small C examples, Philips examples with no make file, my examples using different includes etc.).

Btw, one question in addition: Which function is assigned to each of the three LEDs on the easypdkprog? I would like to add some silkscreen for explanation.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 17, 2020, 08:49:52 pm
Ok, I had the audacity to create a preliminary "lite"-Version of the easypdkprogrammer, based on "Basic" components from the JLCPCB catalogues.

[attachimg=4]

You can find the schematics below. I had to change quite a few parts. I simplified the supply a bit, as discussed above. The functionality should be exactly identical, including the not-yet-used ADC sense lines.

The inductor, USB-port and headers have to be soldered manually. The XTAL is optional, but can still be populated. The switch is also optional. Two pins can be used instead to invoke the bootloader.

The MCU can be either populated by JLCPCB or manually.

Cost for populated PCBs without MCU is $16.95 for five, so $3.39 each. That includes the PCB, but no shipping. Cost with CPU is $26.8 for five, $5.36 a piece.

Let me know if you have additional input. I will most likely test this the next time I order at JLCPC, which could still be a while. If anybody else wants to try, i can share the design files.

p.s.: It seems that EasyEDA has updated all their libraries with slightly increased solder pad sizes. If you update the footprints, a lot of designrules in the easypdkprogrammer pcb are violated.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on May 17, 2020, 10:10:03 pm
You can find the schematics below. I had to change quite a few parts. I simplified the supply a bit, as discussed above. The functionality should be exactly identical, including the not-yet-used ADC sense lines.
You can get rid of another 4 resistors if you connect PB0 & PB1 to the opamp pin 2 & 6
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 05:29:36 am
You can find the schematics below. I had to change quite a few parts. I simplified the supply a bit, as discussed above. The functionality should be exactly identical, including the not-yet-used ADC sense lines.
You can get rid of another 4 resistors if you connect PB0 & PB1 to the opamp pin 2 & 6

True, good observation. But on the other hand I wonder what you would measure then? Effectively you observe the voltage difference between the negative and positive opamp input, the reguluation input. This is basically dependent on opamp gain. So it would vary depending on temperature and part-to-part variation. It would only be a very indirect indicator of supply current.

But the same applies to the implementation as it is now? Adding the resistors costs only fractions of cents, btw.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on May 18, 2020, 05:42:54 am
But on the other hand I wonder what you would measure then?
You measure exactly what you're measuring with the resistor dividers R14/15/16/17, just scaled differently.

This is basically dependent on opamp gain. So it would vary depending on temperature and part-to-part variation. It would only be a very indirect indicator of supply current.
Resistor dividers don't really suffer from temperature dependence. I'm not sure what this has to do with supply current.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 05:46:27 am
But on the other hand I wonder what you would measure then?
You measure exactly what you're measuring with the resistor dividers R14/15/16/17, just scaled differently.

This is basically dependent on opamp gain. So it would vary depending on temperature and part-to-part variation. It would only be a very indirect indicator of supply current.
Resistor dividers don't really suffer from temperature dependence. I'm not sure what this has to do with supply current.

I meant VDD and VPP of the device to be programmed.

The thing is that the operational amplifier can be seen as a device that tries to create a "virtual short" between the positive and negative inputs. So, with a perfect opamp you would basically measure your DAC output voltage at the ADC input. In a real circuit you will measure a small delta, because the gain of the OPAMP is finite. The OPAMP gain however, depends on part-to-part variation, ambient temperature, and supply voltage in a non-predictable way. In addition we will also observe an influence of the opamp output impedance.

But yes, you measure basically the same in both resistor configurations.. The thought experiment of simplifying the schematics just shows that the information to be gained from the sense input is to be treated with caution. You can surely detect a short condition, but any attempt of measuring more nuanced information needs to be scrutinized in respect to the deviation introduced by the opamp.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on May 18, 2020, 06:02:20 am
In a real circuit you will measure a small delta, because the gain of the OPAMP is finite. The OPAMP gain however, depends on part-to-part variation, ambient temperature, and supply voltage in a non-predictable way. In addition we will also observe an influence of the opamp output impedance.
The opamp gain is so large w.r.t. the closed-loop gain that its variance doesn't matter. The input offset voltage would have more of an effect.
The thought experiment of simplifying the schematics just shows that the information to be gained from the sense input is to be treated with caution. You can surely detect a short condition, but any attempt of measuring more nuanced information needs to be scrutinized in respect to the deviation introduced by the opamp.
If you want to measure the VDD/VPP current consumption, keep R14/15/16/17 on the output of the opamp, but add a series resistor (10R should be OK) between there and the header pins; this resistor should be inside the feedback loop. I agree that the sense configuration as currently drawn is not very informative.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 06:41:39 am
The opamp gain is so large w.r.t. the closed-loop gain that its variance doesn't matter. The input offset voltage would have more of an effect.
Good point. Looks like the input offset for the LM358 is 5 mV and the gain is 100dB, so there is at least 2 oom difference wrt to FS output.

If you want to measure the VDD/VPP current consumption, keep R14/15/16/17 on the output of the opamp, but add a series resistor (10R should be OK) between there and the header pins; this resistor should be inside the feedback loop. I agree that the sense configuration as currently drawn is not very informative.

Hm.. the ADC is 12 bit and assuming FS=3.3V we can resolve 0.8 mV per count. The voltage dividers R14-R17 divide by a factor of 6, so we can resolve ~5mV in the higher voltage domain. For a 10 Ohm sense resistor that would correspond to 500µA resolution. A second sense input may be needed for reference. No idea whether this would provide meaningful insight. JS, what was the idea behind the sensing?

In general, it would, of course, make most sense if the lite version behaves identical to the original one.

Edit, changed ratio.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on May 18, 2020, 06:48:33 am
Ok, I had the audacity to create a preliminary "lite"-Version of the easypdkprogrammer, based on "Basic" components from the JLCPCB catalogues.

(Attachment Link)

You can find the schematics below. I had to change quite a few parts. I simplified the supply a bit, as discussed above. The functionality should be exactly identical, including the not-yet-used ADC sense lines.

The inductor, USB-port and headers have to be soldered manually. The XTAL is optional, but can still be populated. The switch is also optional. Two pins can be used instead to invoke the bootloader.

The MCU can be either populated by JLCPCB or manually.

Cost for populated PCBs without MCU is $16.95 for five, so $3.39 each. That includes the PCB, but no shipping. Cost with CPU is $26.8 for five, $5.36 a piece.

Let me know if you have additional input. I will most likely test this the next time I order at JLCPC, which could still be a while. If anybody else wants to try, i can share the design files.

p.s.: It seems that EasyEDA has updated all their libraries with slightly increased solder pad sizes. If you update the footprints, a lot of designrules in the easypdkprogrammer pcb are violated.

Awesome work Tim!
If people can buy a turn-key assembled board from JLC then that wold be awesome, but one-off's aren't practical so someone in each country couldn't make up a bunch on sell locally perhaps?
Don't JLC have a public open source projects thing?
Will this be going back into the git?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: EEVblog on May 18, 2020, 06:52:19 am
You saw Dave struggling when he tried his own "Hello World" (even that there are fully working and pre compiled examples including make files coming with the EasyPDK programmer software... He just overlooked this).
EDIT: Direct link to EasyPDK code examples: https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples  <=============== CODE EXAMPLES

Yep, missed that!
But why didn't the code I had work on the PMS150C?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 07:16:13 am
Awesome work Tim!
If people can buy a turn-key assembled board from JLC then that wold be awesome, but one-off's aren't practical so someone in each country couldn't make up a bunch on sell locally perhaps?
Don't JLC have a public open source projects thing?
Will this be going back into the git?

Thanks a lot! Although the amount of work I had to invest does of course pale to that of the original design.

There are still some things to be clarified before this can be released. I will add some more notes later. The easiest would be to host the files on github with clear instructions how to order.

I agree that economics of this would improve a lot if people shared orders. The MOQ for many of the components is not even reached yet, so the cost would go down further when panelizing and ordering 20 or 50 boards at once. I don't have a good idea how to organize this other than people taking the initiative to redistribute locally.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 18, 2020, 07:28:19 am
Fully agree. To be really honest, we may need to solve the issue of having example code for four different environments first. (Small C examples, Philips examples with no make file, my examples using different includes etc.).

When I wrote my examples, the idea was to have them as part of short tutorials, such as I did for STM8 (and MCS-51) before:

http://www.colecovision.eu/stm8/ (http://www.colecovision.eu/stm8/)

There I am trying to give a full walkthrough on a simple code example to get to "Hello, world!" (or blinking LEDs, or a benchmark - the latter won't work on pdk due to lack of RAM) for oneboard at a time, covering many common boards.

However, the samples also worked well for a workshop on µC-programming for bachelor students (with previous C experience, but no µC experience) that I did a year ago at the university of Freiburg.

I guess in the end, there will be multiple code samples and tutorials by many people anyway; at some point it might be a good idea to have a wiki page or such giving a quick overview / comparison of them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 18, 2020, 09:02:53 am
Hi I whipped up a Code::Blocks wizard for Padauk projects at:

https://github.com/kenyapcomau/codeblocks-wizard-pdk

I don't actually have any hardware at the moment, I just tested with a dummy main.c file with SDCC 3.9 so please raise an issue at the repository if I have got anything wrong. I have a dropdown for pdk14 and pdk15. Should I add pdk13 and pdk16? Which is the best default choice in the dropdown?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 18, 2020, 10:28:52 am
Hi I whipped up a Code::Blocks wizard for Padauk projects at:

https://github.com/kenyapcomau/codeblocks-wizard-pdk

I don't actually have any hardware at the moment, I just tested with a dummy main.c file with SDCC 3.9 so please raise an issue at the repository if I have got anything wrong. I have a dropdown for pdk14 and pdk15. Should I add pdk13 and pdk16? Which is the best default choice in the dropdown?

Thanks.

As of current SDCC 4.0, pdk14 and pdk15 are considered stable, pdk13 is considered experimental / in development (sinceit has recevied less testing that pdk14 and pdk15). We are still quite far away from pdk16 support. So I suggest to have pdk13, pdk14 and pdk15 in the dropdown.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 18, 2020, 10:36:27 am
Ok, done. Dropdown contains pdk{13,14,15}.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 18, 2020, 12:56:13 pm
You saw Dave struggling when he tried his own "Hello World" (even that there are fully working and pre compiled examples including make files coming with the EasyPDK programmer software... He just overlooked this).
EDIT: Direct link to EasyPDK code examples: https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples  <=============== CODE EXAMPLES

Yep, missed that!
But why didn't the code I had work on the PMS150C?

Hi Dave,

the code actually seemed to work. You just did not include the IC calibration. This means, the internal clock of every PADAUK IC differs from part to part so a calibration of the clock frequency is required. EASY PDK Programmer can do this for you. You only need to add a macro and programmer will detect this and tune your IC during writing. Have a look at the examples mentioned in programmer repository (in Examples/src folder).
If you do not tune the IC the SYSCLOCK most likely will 80% to slow or 80% to fast. In your video it was clearly visible, that the serial output was there, just used totally wrong timing..

JS

BTW: MANY THANKS for providing this platform for people like us to discuss and develop this kind of projects!  :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 18, 2020, 01:11:30 pm
Ok, done. Dropdown contains pdk{13,14,15}.

Hi,

could you have a look at the examples from free pdk software: https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src

There are header files for some ICs: https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Examples/src/easypdk
and also examples what you need as minimum when you start a new project.

Especially the tuning of the IC SYSCLOCK:

#include "easypdk/pdk.h"

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V
  return 0;                                     //perform normal initialization
}

void main(void)
{
  //...
}


Compile with one of those lines:

sdcc -DPMS150C -mpdk13 -o myprog_pms150c.ihx myprog.c
sdcc -DPFS154 -mpdk14 -o myprog_pfs154.ihx myprog.c
sdcc -DPFS173 -mpdk15 -o myprog_pfs173.ihx myprog.c


Write to IC with one of this lines:

easypdkprog --icname=PMS150C  write myprog_pms150c.ihx
easypdkprog --icname=PFS154  write myprog_pfs154.ihx
easypdkprog --icname=PFS173  write myprog_pfs173.ihx



Example output when programing IC:
Erasing IC... done.
Writing IC... done.
Calibrating IC (@4.00V IHRC SYSCLK=8000000Hz)... calibration result: 7946104Hz (0x84)  done.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 18, 2020, 01:52:13 pm
Ok I've augmented the sample main program. Also added a hint to define the processor model in project options.

How should I handle the defines for the variants? Currently one chooses the architecture which sets the -m and -l options and any project specific defines are up to the programmer.

If the dropdown is a list of chips implying an architecture, then that list might keep expanding, unlike architectures which expand slowly (only pdk16 expected later). Also each target will have different options, and if a project has multiple targets that can be handled by C::B like this:

http://forums.codeblocks.org/index.php?topic=9277.0 (http://forums.codeblocks.org/index.php?topic=9277.0)
https://imagecraft.com/help/ICCV8AVR/iccavr/3-ide_codeblocks/multi-target_support_and_build_properties.htm (https://imagecraft.com/help/ICCV8AVR/iccavr/3-ide_codeblocks/multi-target_support_and_build_properties.htm)

So I'm inclined to keep the list of architectures in the dropdown as it is now for simplicity and let people who use multiple targets tweak the options.

I don't know how to register and interface programs like easypdkprog to C::B. Maybe a plugin is required, I have to find out.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on May 18, 2020, 03:54:31 pm
I don't know how to register and interface programs like easypdkprog to C::B. Maybe a plugin is required, I have to find out.

I suppose that would fall under the categorisation of a Code::Blocks 'Tool'. That's how I have, for instance, stm8flash and stm8gal set up in C::B. You can use variables in the command-line parameters of each tool for things like the output file, etc.

For example, I have the parameters set up for stm8flash like so:

Executable: C:\[...]\stm8flash.exe
Parameters: -c stlinkv21 -p ${MCU} -s flash -w "${TARGET_OUTPUT_FILE}"
Working Dir: ${PROJECT_DIR}

The MCU variable is defined in the project's build options (e.g. MCU = STM8S208RB).

So, I think in the case of easypdkprog, because the chip model needs to be passed both as a macro definition when compiling, as well as to the programmer command line, then for the new project wizard you'd want it to set up an MCU (or whatever appropriate name) variable in the build options (with value e.g. "PFS154"), then also in build options compiler settings add a #define of ${MCU} (so it gets passed as a -D option to the compiler).

Then, the tool could be configured as follows:

Executable: \path\to\easypdkprog
Parameters: --icname=${MCU} write "${TARGET_OUTPUT_FILE}"
Working Dir: ${PROJECT_DIR}

The one thing I don't know is whether you can have pre-defined tool definitions be installed, or whether they're only user-configurable.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 18, 2020, 04:02:40 pm
Yeah I discovered that too. I see that it's stored in the users global config not in the project config so cannot be generated by a template. So I'll leave it for now.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 18, 2020, 07:21:15 pm
p.s.: It seems that EasyEDA has updated all their libraries with slightly increased solder pad sizes. If you update the footprints, a lot of designrules in the easypdkprogrammer pcb are violated.
So essentially they change something in their library or program, and your project, which was previously completely fine, now requires lot's of changes just to get it into a working shape again. That is why I really dislike cloud services like this.

So I'd prefer if we move to a different EDA suite which is known for being more stable than this. I think the work being done by thomasesr in https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14 (https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14) is the better direction for going forward. A JLCPCB SMT optimized or lite version could then be based on top of that.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 07:33:46 pm
p.s.: It seems that EasyEDA has updated all their libraries with slightly increased solder pad sizes. If you update the footprints, a lot of designrules in the easypdkprogrammer pcb are violated.
So essentially they change something in their library or program, and your project, which was previously completely fine, now requires lot's of changes just to get it into a working shape again. That is why I really dislike cloud services like this.

So I'd prefer if we move to a different EDA suite which is known for being more stable than this. I think the work being done by thomasesr in https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14 (https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14) is the better direction for going forward. A JLCPCB optimized or lite version could then be based on top of that.

No, actually they ask you if you want to update. But if you confirm, your next DRC will look aweful. Probably this can be fixed by adjusting design rules.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 18, 2020, 07:39:39 pm
No, actually they ask you if you want to update. But if you confirm, your next DRC will look aweful. Probably this can be fixed by adjusting design rules.
But can you decline the update, keep the pcb untouched by their updates and still make changes to it?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 18, 2020, 07:40:32 pm
No, actually they ask you if you want to update. But if you confirm, your next DRC will look aweful. Probably this can be fixed by adjusting design rules.
But can you decline the update, keep the pcb untouched by their updates and still make changes to it?

Well, that's what I did after I learned from my mistake :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on May 19, 2020, 02:02:32 am
I suppose that would fall under the categorisation of a Code::Blocks 'Tool'. That's how I have, for instance, stm8flash and stm8gal set up in C::B. You can use variables in the command-line parameters of each tool for things like the output file, etc.

As well as being a tool and outside the scope of the wizard template, I think easypdkprog should be at least wrapped in a shell/cmd script so that it will prompt for the MCU to be inserted and get confirmirmation before burning. I don't have any chips or programmer so that's something for another hacker or another day.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 19, 2020, 10:29:28 am
p.s.: It seems that EasyEDA has updated all their libraries with slightly increased solder pad sizes. If you update the footprints, a lot of designrules in the easypdkprogrammer pcb are violated.
So essentially they change something in their library or program, and your project, which was previously completely fine, now requires lot's of changes just to get it into a working shape again. That is why I really dislike cloud services like this.

So I'd prefer if we move to a different EDA suite which is known for being more stable than this. I think the work being done by thomasesr in https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14 (https://github.com/free-pdk/easy-pdk-programmer-hardware/pull/14) is the better direction for going forward. A JLCPCB optimized or lite version could then be based on top of that.

No, actually they ask you if you want to update. But if you confirm, your next DRC will look aweful. Probably this can be fixed by adjusting design rules.

This looks like a quirks in EasyEDA... I found that it has something to do with IMPERIAL / METRIC settings and rounding.
I could prevent this by switching Units to "mil" in canvas settings, then do the PCB update, then switch back to "mm".

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: wolf22 on May 21, 2020, 10:47:37 am
When I look onto the shown schematics, I think, a usual PIC programmer would do the same job. Just apply a programmable Vcc, a also programmable Vpp and a clock + data.

And do not say, that a STM32F103 cannot do the job. I append a small PIC programmer of my own. Use it as you want (if you want).

Looking on the firmware of the 'easypdkprog' I feel, that it is wrong to implement the algorithms into the programmer hardware. They should remain on the PC side. The firmware of the programmer should do only the basic low level functions, so that any changes in the algorithms do not require any update of the programmer itself.

btw: it also seems to me not useful to have a DIL tht footprint on the programmer. All the Padauk controllers come in SMD and so the board where they reside needs a socket for a kind of programming cable. So the programmer itself only needs to have also a connector for this cable.
regards
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 21, 2020, 11:02:11 am
btw: it also seems to me not useful to have a DIL tht footprint on the programmer. All the Padauk controllers come in SMD and so the board where they reside needs a socket for a kind of programming cable. So the programmer itself only needs to have also a connector for this cable.
regards

Some connector is needed anaway, so it might be as well the DIL footprint. While LCSC currently only stocks SMD parts, according to Padauk datasheets, DIL parts exist.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 21, 2020, 12:20:28 pm

This looks like a quirks in EasyEDA... I found that it has something to do with IMPERIAL / METRIC settings and rounding.
I could prevent this by switching Units to "mil" in canvas settings, then do the PCB update, then switch back to "mm".

Indeed, that could be it. The deviations are usually quite small, so maybe it's a rounding error at minium dimensions.

Btw, could you comment on the functionality of the three LEDS in the easypdkprog? I could not find any documentation, but probably i looked into the wrong place. Would it be ok to remove one so there is space for some text to describe functionality?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 21, 2020, 01:16:43 pm
When I look onto the shown schematics, I think, a usual PIC programmer would do the same job. Just apply a programmable Vcc, a also programmable Vpp and a clock + data.

And do not say, that a STM32F103 cannot do the job. I append a small PIC programmer of my own. Use it as you want (if you want).

...

btw: it also seems to me not useful to have a DIL tht footprint on the programmer. All the Padauk controllers come in SMD and so the board where they reside needs a socket for a kind of programming cable. So the programmer itself only needs to have also a connector for this cable.
regards

Well, the PIC programming protocoll is very similar, so it is no surprise the programmers are functionally similar. There are some extras though, like the clock calibration, that may not be covered with other programmers.
Your programmer uses many different component, so it also does not have a very optimized BOM for production.

I agree about the connector. Best would be to add a connector to a flatband cable for a SOIC8 clamp. That's what I use for ICP.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on May 21, 2020, 01:41:04 pm
btw: it also seems to me not useful to have a DIL tht footprint on the programmer. All the Padauk controllers come in SMD and so the board where they reside needs a socket for a kind of programming cable. So the programmer itself only needs to have also a connector for this cable.
I think the DIL connector was chosen so you can easily plug in a common programming socket. I use this one: https://www.aliexpress.com/item/32716376199.html (https://www.aliexpress.com/item/32716376199.html) and it works quite well.
You can also use a clamp style connector like this one: https://www.aliexpress.com/item/32822110321.html (https://www.aliexpress.com/item/32822110321.html)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DenCraw on May 22, 2020, 10:30:16 am
HI.
Great job!.

any chance to make a simulator?... i know the IC's are cheap but....
anyway again thank's Dave for sharing this amazing work!. i have a  lot to learn now. don't worry I'll RTFM before asking.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: wolf22 on May 22, 2020, 10:34:06 am
Your programmer uses many different component, so it also does not have a very optimized BOM for production.

Yes, this programmer has a quite different approach. It is intended to feed VCC to a board, which may consume more current than the PIC itself would need. Also it is intended to set the voltage on VCC to values from approx. 2 volts to nearly 7 volts from the supply via USB and maintains the logic levels according to this span. That's probably a bigger gun than required for programming a Padauk controller.

But there are some details in the hardware, I would like to point on: the setup of the voltages is separated from the switches, it needs only a usual PWM and it is limited by the choosen values of the resistors, so no fault can occure if the software fails to limit it to the bounds given by the manufacturer.

But this is only a matter of hardware.

My problems with the easypdkprog are software problems, in particular the lacking definitions of the protocol between PC and programmer on the USB. I use to start any development by writing down the interface and protocol between different parts (like PC software and µC firmware), so the whole development can be divided into smaller parts and can be written separately.

And I love to split down the necessary functions of the programmers firmware to atomic ones, so the algorithms can be left on the PC side without making the whole procedere clumsy. If there is an interest in this, I can post it here.

regards
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 23, 2020, 09:57:58 am
HI.
Great job!.

any chance to make a simulator?... i know the IC's are cheap but....
anyway again thank's Dave for sharing this amazing work!. i have a  lot to learn now. don't worry I'll RTFM before asking.

There is some (i.e. core is fully supported, but some peripherals are still lacking) support in the ucsim simulator (it comes with SDCC). Also, for development, you can just use a pin-compatible flash part, rather than an OTP one (however, the flash parts are more expensive, typically in the range of 0.07$ each).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 25, 2020, 08:53:17 am
Your programmer uses many different component, so it also does not have a very optimized BOM for production.

Yes, this programmer has a quite different approach. It is intended to feed VCC to a board, which may consume more current than the PIC itself would need. Also it is intended to set the voltage on VCC to values from approx. 2 volts to nearly 7 volts from the supply via USB and maintains the logic levels according to this span. That's probably a bigger gun than required for programming a Padauk controller.

But there are some details in the hardware, I would like to point on: the setup of the voltages is separated from the switches, it needs only a usual PWM and it is limited by the choosen values of the resistors, so no fault can occure if the software fails to limit it to the bounds given by the manufacturer.
Yeah, one could actually run the bost converter from an PWM output, i know that's also done in some PIC programmers. Or one could use a lowpass filter to get a DC reference voltage. Using a DAC saves some headache for calibration though and one can use an open-loop control. if it is available in the MCU it's a better approach in my books.

My comment was rather referring to the fact that you used many different component types. Not easier to get manufactured than the easypdkprog is now.

Quote
My problems with the easypdkprog are software problems, in particular the lacking definitions of the protocol between PC and programmer on the USB. I use to start any development by writing down the interface and protocol between different parts (like PC software and µC firmware), so the whole development can be divided into smaller parts and can be written separately.

And I love to split down the necessary functions of the programmers firmware to atomic ones, so the algorithms can be left on the PC side without making the whole procedere clumsy. If there is an interest in this, I can post it here.

This sounds a bit like the GNU/Hurd vs. Linux debate (not that I witnessed that first hand...) :) What you are proposing is certainly cleaner from an architecture point of view, but in the end both solutions work equally well for the user. Changing the software now would be a major undertaking.

One thing that could be very interesting though, would be to adopt the Pickit programmer hardware. There are many clones available on eby/aliexpress and the hardware looks like it could support the Paduak.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 25, 2020, 09:19:41 pm
Ok, I had the audacity to create a preliminary "lite"-Version of the easypdkprogrammer, based on "Basic" components from the JLCPCB catalogues.

Is this lite programmer mechanically compatible (i.e. will it fit into the same case as the normal programmer)?

The main problem I see for assembly is the USB connector. Replacing it with a through-hole part, while breaking mechanical compability, would make it easier to hand-solder (as JLCPCB does not solder connectors).

P.S.: Why not just put the design into free-pdk git, as an alternative programmer, to make it easier for people to have a closer look (and github issues might be better for discussion of individual features than this forum thread). We already have 10 repos there, so an 11th one won't hurt.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 30, 2020, 02:16:35 pm
Ok, I finalized revision 0 of the EASYPDKPROG-lite now and ordered a few populated boards for testing purposes. They should arrive in about 3 weeks. I may share some boards after successful testing, since multiple people contacted me asking for one.

[attachimg=1]

The programmer should be mechanically and functionally 100% compatible to the original. I had to change many parts though, to cater for the JLCPBC part selection, and made some simplifications. So there is a risk that the lite version has some yet-to-be-identified quirks.

Almost all parts can be populated by the JLCPCB assembly service. The cost is close to $2 when ordering 50 pc.

The following parts have to be assembled manually:

- The headers
- The power inductor L1
- The USB connector
- Optional: Xtal and push button.

So some assembly is still required. But this will also help to avoid certain regulations on the sales of electronics devices.

for further details, please refer to my design notes in the PDF.
 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 30, 2020, 02:21:44 pm
Is this lite programmer mechanically compatible (i.e. will it fit into the same case as the normal programmer)?

The main problem I see for assembly is the USB connector. Replacing it with a through-hole part, while breaking mechanical compability, would make it easier to hand-solder (as JLCPCB does not solder connectors).

P.S.: Why not just put the design into free-pdk git, as an alternative programmer, to make it easier for people to have a closer look (and github issues might be better for discussion of individual features than this forum thread). We already have 10 repos there, so an 11th one won't hurt.

Yes, it should be 100% mechanically compatible. I considered your proposal of adding a through-hole USB connector. But unfortunately those are only available as A-type plug or socket. Adding them would have required significant changes to the board layout. Also type-A connectors seem to be somewhat outdated. So I stuck with the Micro-B, but moved some components around for easier soldering.

I can add the design files and ordering instructions to the easkypdk repository after testing.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 01, 2020, 01:52:17 pm
Is this lite programmer mechanically compatible (i.e. will it fit into the same case as the normal programmer)?

The main problem I see for assembly is the USB connector. Replacing it with a through-hole part, while breaking mechanical compability, would make it easier to hand-solder (as JLCPCB does not solder connectors).

P.S.: Why not just put the design into free-pdk git, as an alternative programmer, to make it easier for people to have a closer look (and github issues might be better for discussion of individual features than this forum thread). We already have 10 repos there, so an 11th one won't hurt.

Yes, it should be 100% mechanically compatible. I considered your proposal of adding a through-hole USB connector. But unfortunately those are only available as A-type plug or socket. Adding them would have required significant changes to the board layout. Also type-A connectors seem to be somewhat outdated. So I stuck with the Micro-B, but moved some components around for easier soldering.

I can add the design files and ordering instructions to the easkypdk repository after testing.

Hi,

in case this needs to be identified as a board variant (which I think might not be required) it would be a good idea to connect one of the unused STM32 pins (e.g. choose one from PB8-PB15) to GND.
This would make it possible to identify this hardware variant in the firmware and to handle things different in case it's needed.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 01, 2020, 02:28:46 pm
Is this lite programmer mechanically compatible (i.e. will it fit into the same case as the normal programmer)?

The main problem I see for assembly is the USB connector. Replacing it with a through-hole part, while breaking mechanical compability, would make it easier to hand-solder (as JLCPCB does not solder connectors).

P.S.: Why not just put the design into free-pdk git, as an alternative programmer, to make it easier for people to have a closer look (and github issues might be better for discussion of individual features than this forum thread). We already have 10 repos there, so an 11th one won't hurt.

Yes, it should be 100% mechanically compatible. I considered your proposal of adding a through-hole USB connector. But unfortunately those are only available as A-type plug or socket. Adding them would have required significant changes to the board layout. Also type-A connectors seem to be somewhat outdated. So I stuck with the Micro-B, but moved some components around for easier soldering.

I can add the design files and ordering instructions to the easkypdk repository after testing.

Hi,

in case this needs to be identified as a board variant (which I think might not be required) it would be a good idea to connect one of the unused STM32 pins (e.g. choose one from PB8-PB15) to GND.
This would make it possible to identify this hardware variant in the firmware and to handle things different in case it's needed.

JS

I connected PB8 to ground, so the board is identifiable. See circuit and design notes.

In hindsight it would make sense to have one pin to indicate whether a crystal is present and a few others to identify boards. Maybe we can use PB8 to GND to identify boards without crystal? I can add some other ID pins in the final version.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 01, 2020, 02:41:28 pm


I connected PB8 to ground, so the board is identifiable. See circuit and design notes.

In hindsight it would make sense to have one pin to indicate whether a crystal is present and a few others to identify boards. Maybe we can use PB8 to GND to identify boards without crystal? I can add some other ID pins in the final version.

Hi,

Crystal presence can be detected in software :-)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 01, 2020, 03:09:12 pm


I connected PB8 to ground, so the board is identifiable. See circuit and design notes.

In hindsight it would make sense to have one pin to indicate whether a crystal is present and a few others to identify boards. Maybe we can use PB8 to GND to identify boards without crystal? I can add some other ID pins in the final version.

Hi,

Crystal presence can be detected in software :-)

JS

Even better. Is this already implemented?

Well, then I'll keep it as it is and claim "PB8=GND" as identifier for the lite version.

Regards,
Tim
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 01, 2020, 06:33:39 pm


I connected PB8 to ground, so the board is identifiable. See circuit and design notes.

In hindsight it would make sense to have one pin to indicate whether a crystal is present and a few others to identify boards. Maybe we can use PB8 to GND to identify boards without crystal? I can add some other ID pins in the final version.

Hi,

Crystal presence can be detected in software :-)

JS

Even better. Is this already implemented?

Well, then I'll keep it as it is and claim "PB8=GND" as identifier for the lite version.

Regards,
Tim

Just a heads up... before you make new version.

Right now I'm working on supporting new flash types from PADAUK (PFS172 / PFC...). It looks like programing sequence changed. Now not sending high voltage on VPP (PA5) but on VDD instead. Looks like after CMD phase (2V voltage difference between VDD and VPP, e.g. 2.5 VDD / 4.5 VPP) new protocol sets VPP to 0 for read/erase/write and VDD needs to be 8.3V for write.

==> Right now programmer can not create 8.3V on VDD (we might need to change R6, maybe same value as R8 so both opamp outputs can produce same levels).

Still investigating.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 01, 2020, 06:49:16 pm
[attachimg=2]

Just a heads up... before you make new version.

Right now I'm working on supporting new flash types from PADAUK (PFS172 / PFC...). It looks like programing sequence changed. Now not sending high voltage on VPP (PA5) but on VDD instead. Looks like after CMD phase (2V voltage difference between VDD and VPP, e.g. 2.5 VDD / 4.5 VPP) new protocol sets VPP to 0 for read/erase/write and VDD needs to be 8.3V for write.

==> Right now programmer can not create 8.3V on VDD (we might need to change R6, maybe same value as R8 so both opamp outputs can produce same levels).

Still investigating.

JS

Thanks for the heads up. I need to change the board anyways for mass production to find a better position for the mounting holes. There will be a "r1".

Regarding the PFS172: It seems it supports two programming modes, right? This is described in unusual detail in the datasheet. The current revision of easypdkprog should be able to support the limited voltage programming mode. They just don't mention why one needs the "normal mode" at all...

[attachimg=1]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 02, 2020, 10:12:09 am
@tim_

Thanks for reminding me of the limited voltage mode. I saw the higher VDD in data sheet and also measured it during programing but forgot about the limited voltage mode :-)

I will try to use this with writer and report back.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 02, 2020, 11:32:22 am
Regarding the PFS172: It seems it supports two programming modes, right? This is described in unusual detail in the datasheet. The current revision of easypdkprog should be able to support the limited voltage programming mode. They just don't mention why one needs the "normal mode" at all...

Maybe the reduced volatge programming mode has reduced retention? Or programming is slower?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 02, 2020, 03:53:29 pm
Regarding the PFS172: It seems it supports two programming modes, right? This is described in unusual detail in the datasheet. The current revision of easypdkprog should be able to support the limited voltage programming mode. They just don't mention why one needs the "normal mode" at all...

Maybe the reduced volatge programming mode has reduced retention? Or programming is slower?

They have a minimum retention specification, so I guess both modes are equeal in that regard. 

It being about programming speed seems more likely. I assume they use a HCI-MTP IP, so the programming speeds depend on voltage and current. I guess programming time is an important cost factor for many of their customers. Maybe not so much for us...



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 08, 2020, 08:37:45 pm
Regarding the PFS172: It seems it supports two programming modes, right? This is described in unusual detail in the datasheet. The current revision of easypdkprog should be able to support the limited voltage programming mode. They just don't mention why one needs the "normal mode" at all...

Maybe the reduced volatge programming mode has reduced retention? Or programming is slower?

Hi,

I think I figured out "limited voltage" programing.

The logic analyzer capture showed the trick:

Programing needs 4 words on PFS172 to be programmed at same time.

In limited voltage programming mode VDD is set to 5.3V and only 1 of the 4 words is programmed (the other 3 words are all '1's, so nothing will change during programming).
After the first word is programmed, the second word of this group is programmed, ...

so instead of programing

A W W W W

it will take 4 passes:

A W X X X
A X W X X
A X X W X
A X X X W

then address is incremented and next 4 word group is programmed.

Address(A), Word(W), AllOnes(X)


This also might be a nice trick to make a real cheap programmer for the flash variants (e.g. using the 5V of Arduino and a 2 resistor voltage divider to have a second voltage to enter programing mode)


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 09, 2020, 04:27:40 am
Hello All,

I've been watching this thread off and on for over a year now, and finally have a few projects that I'm itching to try.  Obviously, getting a working programmer and some ICs is the first step, and that is what has held me back for a while.  But, it looks like things have progressed to a point where I think I'll jump in.  Thanks everyone for all your hard work on this!

Anyway, I spent some time today familiarizing myself with the programmer hardware schematics, and noticed that the base portion is roughly the same as the infamous STM32 blue-pill boards.  So, I ended up creating a (mostly compatible) variation that is a top-hat for said boards.  This is smaller than the original programmer, so it will be a bit cheaper to get one-offs produced (well technically 3-offs... $4.80 for 3x shipped from OSHPARK).

Important: Because the blue-pill's STM32F103C8T6 doesn't offer a DAC, it will have to be replaced with the STM32F072C8T6 that the original programmer uses (they are pin compatible), or possibly the software would have to be modified to use PWM instead of DAC (might not be easy/possible).  Also if the LEDs are populated, the blue-pill's 32kHz crystal and supporting capacitors may need to be removed.

The schematic (attached), aside from missing the STM32, USB, Vreg, etc... is exactly the same (with the same ref #'s as well), except for these minor changes:

Here are the components that the blue-pill board already populates, and therefore are not in my schematic or on my board:

I sent these boards off to OSHPARK (https://oshpark.com/shared_projects/z5EAm6HO) to get produced and will build one up when they get back in a few weeks.  Hopefully I didn't mess up anything to badly on the schematic.  Assuming all goes well, I'll publish the source files as well (I used Kicad).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 09, 2020, 07:52:47 am
Due to the high number of different pinouts on the 8-pin Padauk devices, I had to create five different variants of the minimal evaluation boards:

https://github.com/free-pdk/f-eval-boards

Thanks to easypdkprog, three of them have been tested (for a total of 5 µC-board combinations), and work well. Corresponding demo programs are at

https://github.com/free-pdk/sdcc-pdk-code-examples

The goal is to have a board for every Padauk flash device (as a side effect, there are some µC that fit on multiple boards).

P.S.: From the table in the README it looks as if the f-eval-pdk-s08b board is redundant. It was created since the PFC161, despite also having the S08A package listed in the datasheet currently is available in S08B package only.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 09, 2020, 01:16:41 pm
  • PB0/PB1 was moved to PA0/PA1.  This kept the final board size smaller and means the blue-pill's boot mode jumpers aren't blocked.  I don't think this will be a problem, although it will require a software modification, and
This should not be a problem at all. It also can be used to auto detect the programmer variant.

  • PA15 isn't connected to BOOT0 (although it could be with a bodge wire).  Not sure why it is on the original?
This connection is intended to also have the button state on a GPIO so the programmer can be used in stand alone mode (later) - firmware is stored in MCU flash, no computer attachached, press button to program IC.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 09, 2020, 02:38:04 pm

Hi,

I think I figured out "limited voltage" programing.

The logic analyzer capture showed the trick:

Programing needs 4 words on PFS172 to be programmed at same time.

In limited voltage programming mode VDD is set to 5.3V and only 1 of the 4 words is programmed (the other 3 words are all '1's, so nothing will change during programming).
After the first word is programmed, the second word of this group is programmed, ...

so instead of programing

A W W W W

it will take 4 passes:

A W X X X
A X W X X
A X X W X
A X X X W

then address is incremented and next 4 word group is programmed.

Address(A), Word(W), AllOnes(X)


This also might be a nice trick to make a real cheap programmer for the flash variants (e.g. using the 5V of Arduino and a 2 resistor voltage divider to have a second voltage to enter programing mode)


JS

Ah ok, that makes a lot of sense. When I tried to program the PFS154 with my Arduino based contraption I had to resort to the same approach of only writing one byte at a time. Apparently the programming mode is somehow current limited and writing fewer bits at the same time allows programming when less current is available.

That's good news, because then the only impact of low-voltage programming is that the writing is slower. This is propbably quite inconsequential for us.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 02:26:08 am
Ok, I was thinking more about the programmer top-hat that I posted a few posts up, and pcbs are so much fun to design and order, so I decided to go ahead to create a bottom board to go along with it.  I call this the STM32 Mini-Pill.  It is essentially 1/2 of the infamous "Blue-Pill" board, and also has a very similar schematic to the STM parts of the original free-pdk programmer.

Combining both modules together essentially nets the same thing as the original programmer (with the slight differences called out above).  The only real 'advantages' are: a smaller size (stacked instead of long), possibly easier hand soldering (uses 0805 instead of 0603), and a base-board module that can be re-used with other projects.  That last point is key for me.  I don't want more than a couple of Padauk programmers, but I could see myself using a larger number of these base-board modules.  So, one can place a small order for the top-hat, and a larger order of the Mini-Pill if desired (or just use the Blue-Pill with the required modifications listed above).

I ordered up a set from OSHPARK for $4.50 for 3x (including free shipping), and will build them up when I get all the parts in.  (https://oshpark.com/shared_projects/8USgL5pT)

The Schematic and Gerber files are attached.  I will post the original Kicad files somewhere after testing everything.

Aside from the obvious parts, I used the following footprints:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 02:33:36 am
This should not be a problem at all. It also can be used to auto detect the programmer variant.
JS, thanks for the confirmation.   :-+  I was looking at the source code, and if I am reading it correctly, it looks like I would only need to modify the code to use ADC 0/1 instead of ADC 8/9.  Does that sound right?

This connection is intended to also have the button state on a GPIO so the programmer can be used in stand alone mode (later) - firmware is stored in MCU flash, no computer attachached, press button to program IC.
Ahh... that makes sense.  I included it on the STM32 Mini-Pill that I just posted.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 02:38:17 am
Due to the high number of different pinouts on the 8-pin Padauk devices, I had to create five different variants of the minimal evaluation boards:

https://github.com/free-pdk/f-eval-boards

spth:  I was looking at this repo yesterday and found myself desiring to see a preview of these boards.  Maybe there is one somewhere and I just didn't see it?  I'm not even sure what to do with the .sch and .lht files to generate my own.  (What tool are those files for?)  Would it be possible for you to upload some .pngs of the boards and schematics to the repo?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 02:45:56 am
This also might be a nice trick to make a real cheap programmer for the flash variants (e.g. using the 5V of Arduino and a 2 resistor voltage divider to have a second voltage to enter programing mode)

JS, that sounds pretty neat.  Would this approach work for all the flash based parts, or only the newer ones?  For now, because of availability and cost, I find the PFS154 and PFS173 to be more interesting than the PFS172 which isn't currently stocked at lcsc.

Also, do you know the current status of the PMS152 when used with the easy-pdk-programmer?  Is it still read-only, or has the write mode been written/tested?  The PCS152-S16 is currently the cheapest 16-pin variant on lcsc and I was thinking of picking some up in addition to the flash variants if they are likely to work.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 10, 2020, 02:09:51 pm
spth:  I was looking at this repo yesterday and found myself desiring to see a preview of these boards.  Maybe there is one somewhere and I just didn't see it?  I'm not even sure what to do with the .sch and .lht files to generate my own.  (What tool are those files for?)  Would it be possible for you to upload some .pngs of the boards and schematics to the repo?

Tools are noted in the README:

Quote
Tools used:

* gschem for the schematic (symbols used to be found in pdk-gschem-symbols repository)
* pcb-rnd for the pcb design

So far I have not added any generated files (I am still unsure if the repo should contain sources only vs. also some genrated files). Would adding some photographs of the assembled boards help (even though it would show how bad I am at hand-soldering)?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: coppice on June 10, 2020, 03:29:17 pm
Padauk is not making any money selling the programmer, so why don't ask them for the programming protocol?
Companies are reluctant to publish information that might want to change at any time. If they want to alter the silicon, maybe to change fabs or for a die shrink, and change the protocol, its a nightmare trying to deal with an open ended set of tools.
Adding support for  universal programmers like TL866 can help sell tons of 3cent microcontrollers.
Nobody buys a ton of parts and programs them with a tool like the TL866. People only program handfuls with a TL866, and nobody gets rich selling 3 cent parts by the handful.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 05:40:34 pm
Would adding some photographs of the assembled boards help (even though it would show how bad I am at hand-soldering)?
Yes, photos of the boards would help a lot!  If possible, a screenshot of the schematics would also help.  Having both of these would allow people to review/troubleshoot without downloading files and opening them in an external program.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 10, 2020, 05:48:29 pm
Padauk is not making any money selling the programmer, so why don't ask them for the programming protocol?
Companies are reluctant to publish information that might want to change at any time. If they want to alter the silicon, maybe to change fabs or for a die shrink, and change the protocol, its a nightmare trying to deal with an open ended set of tools.
I realize you are responding to a several year old post, and I agree that Padauk is not likely to release the programming protocol, unfortunately.  But, I would imagine if they did change the silicon in a way that changed the programming protocol they would also have to release an update to their own programmer and they would probably release the IC with a different part number anyway.

And, there are many vendors that DO release programming information.  Take a look at Atmel's AVR datasheets, or TI's for their CC series.  There is enough information contained within to build a custom programmer.  Maybe that is part of why Atmel's AVRs were/are so successful (i.e. their openness on programming protocols and instruction set encoding and so forth helped pave the way for avr-gcc and avrdude and ultimetly Arduino).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 09:17:20 am
Would adding some photographs of the assembled boards help (even though it would show how bad I am at hand-soldering)?
Yes, photos of the boards would help a lot!  If possible, a screenshot of the schematics would also help.  Having both of these would allow people to review/troubleshoot without downloading files and opening them in an external program.

I'v added both now (though I left out the photo of the f-eval-pdk-s08b with PFC161, since my hand-soldering looks worst there):

https://github.com/free-pdk/f-eval-boards/tree/master/photos
https://github.com/free-pdk/f-eval-boards/tree/master/drawings
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 09:37:32 am
For now, because of availability and cost, I find the PFS154 and PFS173 to be more interesting than the PFS172 which isn't currently stocked at lcsc.

Also, do you know the current status of the PMS152 when used with the easy-pdk-programmer?  Is it still read-only, or has the write mode been written/tested?  The PCS152-S16 is currently the cheapest 16-pin variant on lcsc and I was thinking of picking some up in addition to the flash variants if they are likely to work.

Well, it is good to have device support early, getting ahead of LCSC a bit.
One device I am looking forward to (said to be released in Q3) is the PGC434. Though the biggest (28-pin) variant is likely to be DIP package only on release (I guess I'll make an evaluation board with through-hole parts only when datahseets become available).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 03:58:34 pm
Well, it is good to have device support early, getting ahead of LCSC a bit.
Oh yes, I agree completely.  Actually, I forget my original point now...  I think it was more around wondering if the low voltage programming would also work on the earlier (already widely available) flash parts PFS154 and PFS173, or if those are only high voltage programmable.  If the low voltage mode would work on those, it would be interesting to work on a much cheaper / more available programmer to potentially accelerate adoption.

One device I am looking forward to (said to be released in Q3) is the PGC434.
That does indeed look interesting (depending on cost).  Where did you find that it would be released in Q3?  I do see it referenced in this doc (https://www.netvisiontek.com/pdfs/selection_guide_2019H1__20190227_EN.pdf (https://www.netvisiontek.com/pdfs/selection_guide_2019H1__20190227_EN.pdf)), but am not finding much information otherwise.  I suppose since it is a multi FPPA IC, using SDCC would be out of the question for now, right?  Maybe I understand incorrectly, but I thought the easy pdk programmer only works with SDCC .hex files, and not output from the official compiler?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 04:18:28 pm
I'v added both now (though I left out the photo of the f-eval-pdk-s08b with PFC161, since my hand-soldering looks worst there):
Thank you!  Those photos and drawings are very helpful.  And your soldering looks fine.  :-+

I noticed that you opened an issue on github about moving from gEDA schem to leptop.  Is there a reason you aren't considering KiCad, which as far as I know, has a much broader user base and is more cross platform compatible?  I would be more than happy to convert the files over for you, if interested.

And, a couple of questions about the schematics:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 04:21:45 pm
Oh yes, I agree completely.  Actually, I forget my original point now...  I think it was more around wondering if the low voltage programming would also work on the earlier (already widely available) flash parts PFS154 and PFS173, or if those are only high voltage programmable.  If the low voltage mode would work on those, it would be interesting to work on a much cheaper / more available programmer to potentially accelerate adoption.
According to the datasheets, both support a limited-voltage programming mode.
Quote
One device I am looking forward to (said to be released in Q3) is the PGC434.
That does indeed look interesting (depending on cost).  Where did you find that it would be released in Q3?  I do see it referenced in this doc (https://www.netvisiontek.com/pdfs/selection_guide_2019H1__20190227_EN.pdf (https://www.netvisiontek.com/pdfs/selection_guide_2019H1__20190227_EN.pdf)), but am not finding much information otherwise.  I suppose since it is a multi FPPA IC, using SDCC would be out of the question for now, right?  Maybe I understand incorrectly, but I thought the easy pdk programmer only works with SDCC .hex files, and not output from the official compiler?

We don't know yet if the PGC434 will be pdk15 or pdk16. If the former, SDCC could still be used when using only one FPPA. But AFAIK, that would then be Padauk's first multi-FPPA pdk15 device. If the latter, it could indeed not be used with current SDCC.

An SDCC pdk16 port for only one FPPA would still be easy to do, but for now we don't even have a fully working assembler / linker - there is an SDCC branch for such basic pdk16 support, but it has not seem much activity recently: https://sourceforge.net/p/sdcc/code/HEAD/tree/branches/pdk/ (https://sourceforge.net/p/sdcc/code/HEAD/tree/branches/pdk/)

Finishing the pdk16 assembler / linker support wouldn't require much knowledge of the rest of SDCC, I guess one could just go by the example of the pdk13, pdk14, pdk15 assemblers and the documentation on GitHub.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 04:32:32 pm
I see two capacitors, one on the USB input of 0.1uF and one on the MCU side of the diode that is 0.01uF.  I assume the one on the MCU side of the diode is a bypass capacitor?  If so, why not the more normal 0.1uF/100nF for that one?
Yes, it is a bypass capacitor. According to the datasheets, 0.01 µF is both the recommended value and the maximum allowed for in-circuit programming. Apparently during programming, VDD needs to change quickly, and higher capacitance would interfere with that.
Quote
And, what is the point of the capacitor on the USB side of the diode?
But 0.01 µF also seems a bit low, especially when the board is powered via a potentially long USB cable, so I added another capacitor on the USB side.
Quote
Speaking of the diode, I assume it is just there to make sure voltage isn't back-fed into the USB connector if you happen to power this through the programmer or breadboard pins, right?
The main purpose is indeed to protect a USB hub, port, or whatever the other end of the USB connector is plugged in, from back-fed voltage. And it allows me to place that extra capacitor.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 04:54:49 pm
I finally got around documenting my last project with the Padauk MCU. It's a chainable 7 segment disaply, where each segment is controlled by PFS154.

It's not too exciting, but I thought it was a suitable application for a 3 cent MCU and is a nice testbed to play around with networking protocols.

You can find a writeup here: https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/ (https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/)

Btw, one nice trick I found during the design was to use a SOIC8-clamp for programming (see attachment). All Padauk MCU have their supply and programming pins arranged in a way that easily allows doing this. No need to add any ISP connectors. You can get these very cheap on aliexpress and ebay.

tim_, Awesome project!  It really helps show the usefulness of such inexpensive devices.

I was reading through your article and source code last night and had a couple of thoughts that I wonder if you had considered:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 05:03:36 pm
I see two capacitors, one on the USB input of 0.1uF and one on the MCU side of the diode that is 0.01uF.  I assume the one on the MCU side of the diode is a bypass capacitor?  If so, why not the more normal 0.1uF/100nF for that one?
Yes, it is a bypass capacitor. According to the datasheets, 0.01 µF is both the recommended value and the maximum allowed for in-circuit programming. Apparently during programming, VDD needs to change quickly, and higher capacitance would interfere with that.
Thanks for the clarification.  I am looking at the datasheet for the PFS154, and on page 85 it mentions a capacitor on VDD/GND of less than or equal to 0.1uF.  I don't see any mention of 0.01uF.  Did that come from a different datasheet?  Also, the easy-pdk programmer itself already has a 0.1uF capacitor on the VDD line.  Are these in conflict with each other then?

And, what is the point of the capacitor on the USB side of the diode?
But 0.01 µF also seems a bit low, especially when the board is powered via a potentially long USB cable, so I added another capacitor on the USB side.
Ok, that makes sense.  Surely something 1uF or higher would be better here, right?  I guess it is a 0805, so higher uF caps can be installed as needed.

Speaking of the diode, I assume it is just there to make sure voltage isn't back-fed into the USB connector if you happen to power this through the programmer or breadboard pins, right?
The main purpose is indeed to protect a USB hub, port, or whatever the other end of the USB connector is plugged in, from back-fed voltage. And it allows me to place that extra capacitor.
Yep, makes sense.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 06:41:21 pm
I see two capacitors, one on the USB input of 0.1uF and one on the MCU side of the diode that is 0.01uF.  I assume the one on the MCU side of the diode is a bypass capacitor?  If so, why not the more normal 0.1uF/100nF for that one?
Yes, it is a bypass capacitor. According to the datasheets, 0.01 µF is both the recommended value and the maximum allowed for in-circuit programming. Apparently during programming, VDD needs to change quickly, and higher capacitance would interfere with that.
Thanks for the clarification.  I am looking at the datasheet for the PFS154, and on page 85 it mentions a capacitor on VDD/GND of less than or equal to 0.1uF.  I don't see any mention of 0.01uF.  Did that come from a different datasheet?  Also, the easy-pdk programmer itself already has a 0.1uF capacitor on the VDD line.  Are these in conflict with each other then?

Which PFS154  datasheet? In version 1.03 of the datasheet, page 87 I see the less than or equal to 0.1 µF. In version 1.05, page 89 it is less than or equal to 0.01 µF.

easy-pdk programmer has in it it needs to be able to deal with. I guess Padauk datasheets assume their programmer (another programmer might be able to sink or source current more quickly to charge or discharge the capacitor).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 06:48:55 pm
And, what is the point of the capacitor on the USB side of the diode?
But 0.01 µF also seems a bit low, especially when the board is powered via a potentially long USB cable, so I added another capacitor on the USB side.
Ok, that makes sense.  Surely something 1uF or higher would be better here, right?  I guess it is a 0805, so higher uF caps can be installed as needed.

AFAIK, bigger capacitors tend to be slower, and I wanted this one to be fast (despite begin seperated fromt he chip by a diode, it is till placed quite close), but I guess we could go a bit bigger, 0.22 µF maybe.
I also wouldn't want to go to full 1 µF or above for another reason: I'd like to leave plenty of headroom in case someone wants to add other components via the pins, e.g. on a breadboard. And the USB spec has an upper limit on the total capacitance of 10 µF.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 07:00:06 pm
I see two capacitors, one on the USB input of 0.1uF and one on the MCU side of the diode that is 0.01uF.  I assume the one on the MCU side of the diode is a bypass capacitor?  If so, why not the more normal 0.1uF/100nF for that one?
Yes, it is a bypass capacitor. According to the datasheets, 0.01 µF is both the recommended value and the maximum allowed for in-circuit programming. Apparently during programming, VDD needs to change quickly, and higher capacitance would interfere with that.
Thanks for the clarification.  I am looking at the datasheet for the PFS154, and on page 85 it mentions a capacitor on VDD/GND of less than or equal to 0.1uF.  I don't see any mention of 0.01uF.  Did that come from a different datasheet?  Also, the easy-pdk programmer itself already has a 0.1uF capacitor on the VDD line.  Are these in conflict with each other then?

Which PFS154  datasheet? In version 1.03 of the datasheet, page 87 I see the less than or equal to 0.1 µF. In version 1.05, page 89 it is less than or equal to 0.01 µF.

easy-pdk programmer has in it it needs to be able to deal with. I guess Padauk datasheets assume their programmer (another programmer might be able to sink or source current more quickly to charge or discharge the capacitor).

Ahh yes... I was looking at the one from lcsc, which is even older (1.02).  Interesting that they would change the recommendation between datasheets.  Although, in 1.05, there is a bit of a discrepancy.  Or more accurately, apparently it depends on whether one is using normal programming mode (for off board programming?), or limited-voltage programming mode (for in circuit programming?) .  On page 89 the 0.01uF is under the Normal Programming Mode section, which seems to be intended for bare IC programming with the programmer (although I'm not really sure what they mean by Multi-Chip-Package).  The eask-pdk's capacitor is probably sufficient here, although technically over the limit.  On page 90, which seems to be referring to On-Board (in-circuit) programming (using Limited-Voltage Programming Mode) it refers to less than < 500uF.  Since this is a dev board (i.e. in-circuit programming) maybe it should be targeting the On-Board/In-Circuit/Limited-Voltage mode that JS is working on?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 07:01:04 pm
I noticed that you opened an issue on github about moving from gEDA schem to leptop.  Is there a reason you aren't considering KiCad, which as far as I know, has a much broader user base and is more cross platform compatible?  I would be more than happy to convert the files over for you, if interested.
I don't design electronics often (so I definitely don't want to put much time into learning new tools), but when I did in the past I used gEDA. Now the original gEDA looks more and more like a dead end. But with pcb-rnd fork of pcb and lepton fork of the rest of gEDA are well-maintained successors available, so I can continue that way.

Quote
The LEDs are configured backwards compared to what I am used to seeing.  Usually the MCU sinks them down to ground instead of sourcing voltage to them.  I think this is because most MCUs are able to sink current better than sourcing it.  I'm not as familiar with the Padauk MCUs yet, but wondering if you took that into consideration?

Typically, there is not much difference between source and sink current on the Padauk µC. For a lot of µC, most pins just have 5 mA sink and source current. There are exceptions, such as the open-drain PA5 on the PFS173, and the PFS154 has a few pins that have 10 mA sink current, but 5 mA source curent. But for the LEDs protected by their 15 k resistors, not much current is needed anyway.

So in the end it comes down to what is most likely to be a good choice for someone wanting to connect something extra to those pins, e.g. on a breadboard. At the time I thought this arrnagement might be better. The 15 k resistors should also help a lot with that. In particular anyone wanting to use those pins for input from some device with open-drain outputs can easily use additional pullups on them.

P.S.: The LED configuration could surely be changed if there is an advantage to doing so.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2020, 07:04:57 pm
Since this is a dev board (i.e. in-circuit programming) maybe it should be targeting the On-Board/In-Circuit/Limited-Voltage mode that JS is working on?

These boards are quite minimal, so for now I'm just trying to keep them compatible with both modes.

That might be less of a priority for a future board with a bit more features that I intend design once the PGC434 datasheet becomes available.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 11, 2020, 07:20:22 pm
Since this is a dev board (i.e. in-circuit programming) maybe it should be targeting the On-Board/In-Circuit/Limited-Voltage mode that JS is working on?

Thess boards are quite minimal, so for now I'm just trying to keep them compatible with both modes.

That might be less of a priority for a future board with a bit more features that I intend design once the PGC434 datasheet becomes available.
Fair enough, although you may want to think about adding the isolation (>10k resistors or <220p capacitors) to pins PA3, PA5, PA6 that they talk about in the On-Board wiring section on page 90.  Actually, if you moved the 15k resistors and LEDs to these pins, you could kill two birds with one stone potentially.  And it would make things more consistent between boards, as some of the smaller ICs don't even have PBx pins.  Might want to make them sink instead of source if you did that based on the comment on page 90: "In general, the writing signal pins PA3, PA5 and PA6 SHOULD NOT be considered as strong output pins."

Thank you for taking the time to explain your design choices.  I will probably create my own version anyway, as my priorities are a bit different.  For one, I would rather have a narrower board that is a bit more optimized for use in a breadboard.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 13, 2020, 06:01:14 am
Thank you for taking the time to explain your design choices.  I will probably create my own version anyway, as my priorities are a bit different.  For one, I would rather have a narrower board that is a bit more optimized for use in a breadboard.

Thanks for taking the time to review the boards.
If you need something narrow for breadboards, directly using DIP devices might also be an option for you.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 13, 2020, 06:32:27 am
I usually use stock breakout-boards when I want to test a device on a breadboard. See pic. You can get them on ebay or aliexpress for next to nothing.

[attach=1]

One topic I can really relate to is that there are many breakout boards that have too much PCB overhang next to the headers. This basically wastes one row of pins for nothing. Philipp, your boards are also guilty of this, see pic :). Also, how about introducing some silkscreen description of the pins and the device? I would also add a copper fill as a ground plane as best practice, but it probably has little impact in this case.

[attach=2]

On other occasions, I have directly mounted the device in the target circuit and used a SOIC clamp for programming.

[attach=3]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 13, 2020, 06:45:49 am
I finally got around documenting my last project with the Padauk MCU. It's a chainable 7 segment disaply, where each segment is controlled by PFS154.

It's not too exciting, but I thought it was a suitable application for a 3 cent MCU and is a nice testbed to play around with networking protocols.

You can find a writeup here: https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/ (https://cpldcpu.wordpress.com/2020/04/05/addressable-7-segment-display/)

tim_, Awesome project!  It really helps show the usefulness of such inexpensive devices.
Thanks!
Quote
I was reading through your article and source code last night and had a couple of thoughts that I wonder if you had considered:
  • Because you are only using 5 of 8 bits, I think it would be fairly easy to add autobaud capabilities to support a much wider (and variable) range of baud rates.  Basically make sure that bit 0 is always a '1' and then the length of the start bit can be measured to use for the delay loops
Yes, there are many protocol enhancements and variants that could be tested. Autobauding is a nice idea. One could also do direct clock recovery by introducing pseudo-manchester? The challenge is to combine this with a standard UART interface, although one could also move away from that.

Quote
  • The EOF could be removed by instead using a counter variable on the idle state (slightly more efficient protocol).  So, inside the interrupt (re-)set a counter variable to 255 (or some number) and then in the main loop decrement the counter variable and enable/change the output when it reaches 0.  So, as long as new bytes are being shifted in, the counter variable keeps getting reset, but once idle the output gets latched after some short delay.  Obviously the delay would have to be longer than the expected time between each byte for this to work right.
EOT by timeout: This is how it is done in the WS2812. I opted not do go this way, because it forces stringent timing requirements on your protocol. What if the datastream from the host-device is paused for some reason, for example an interrupt or a task switch?
Quote
  • It looks like there are two extra pins available, so it seems like a single IC could easily support two 7-segment displays by using multiplexing.  Obviously it would mean adding two transistors or mosfets and changing the main loop to time divide between the two, and the interrupt code to stay in receive mode for longer.  But might be slightly cheaper end result, and how often is just one 7-segment useful anyways.  EDIT:  Actually I just noticed that there are two other pins that are only being used for ICP that could also be used to make a 4x 7-segment multiplexed display with one IC.  If on-board programming is needed, isolation resistors might be required.
Sure, but the point of the design was to use one MCU per Display :)
Quote
  • Another thought is that it is unlikely to often need a chain of more than about 8 of these to begin with, so potentially the 3 un-used bits in each byte could be used as an address, meaning each one could be directly connected to the input (instead of being chained), and they would only update when their address matched.  Now that I think about some more, each one would have to know what their address is, which would mean giving up on 2 displays per MCU (need the pins for address setting), and would also have to give up on autobaud (need all 3 un-used bits), and would be limited to only 8 displays, so probably not worth looking into.
Well, why would you limit it to 8 devices? But anyhow, one could also imagine a protocol with packet routing that directly allows to address specific devices. There could be an autonumeration phase where the devices assign addresses to themselves based on the position in the chain.
Quote
  • I'm curious if the current limiting resistor is needed at all?  It looks like the IO pins can only source/sink so much current anyway, although it is unclear if damage would occur without the resistor, or if the IO pins would just naturally limit the current?
The output drivers of the PDK MCUs are unusually weak. They barely drive 10mA. You can connect any LED to it without series resistor. Whether that is a good and stable design is another question, though...
Quote
  • Final thought (for now)... I wonder if it is possible/useful to implement sleep mode after setting/changing the outputs?  The pin change interrupt will wake the device when communication occurs, although it might take longer for the interrupt to be invoked (has this latency been tested yet?)  Again, this may not be worth it because these MCUs take less than 1mA anyways (a fraction of what the 7-segment LEDs take), and if using two display with multiplexing then sleep mode gets more complicated (might be able to use a wake-up timer to sleep between alternating digits).  Another option might be to lower the system clock when doing the multiplexing in the main loop, and raise it again in the interrupt (again not sure how that impacts the interrupt latency)

Yes, sleep mode would make a lot of sense and is easy to implement, since the RX already uses an interrupt.

Right now I am not planning to continue working on the project though. If you have a pull request, feel free to submit something :)
[/list]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 13, 2020, 09:52:55 am
One topic I can really relate to is that there are many breakout boards that have too much PCB overhang next to the headers. This basically wastes one row of pins for nothing. Philipp, your boards are also guilty of this, see pic :).
On the other hand, that overhang makes it easier to route stuff (e.g. to the LEDs and the programming header). But feel free to open an issue on GitHub, so I'll check if I could reroute to save that one row on each side. [Edit: I just opened the issue myself: https://github.com/free-pdk/f-eval-boards/issues/3]
Quote
Also, how about introducing some silkscreen description of the pins and the device?
I don't want to add silkscreen forthe device (as each board can be used for multiple devices, as long as thtey have the same pinout. But I indeed want to add silkscreen for the pins in the next version.
Quote
I would also add a copper fill as a ground plane as best practice, but it probably has little impact in this case.
There already is (on the bottom side).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 13, 2020, 10:01:46 am
One topic I can really relate to is that there are many breakout boards that have too much PCB overhang next to the headers. This basically wastes one row of pins for nothing. Philipp, your boards are also guilty of this, see pic :).
On the other hand, that overhang makes it easier to route stuff (e.g. to the LEDs and the programming header). But feel free to open an issue on GitHub, so I'll check if I could reroute to save that one row on each side.

You could reduce the copper trace width for easier routing. Since the Padauk cannot drive high currents anyways, 10mil lines should be more than sufficient.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 13, 2020, 11:23:38 am
You could reduce the copper trace width for easier routing. Since the Padauk cannot drive high currents anyways, 10mil lines should be more than sufficient.

40 mA seems to be the maximum drive / sink current, so if necessary, I could indeed go below the currently used 20 mil.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 13, 2020, 06:51:34 pm
If you need something narrow for breadboards, directly using DIP devices might also be an option for you.]

Yeah, but that means stocking different size ICs (and I didn't see the DIP one available on LCSC) and dealing with all the hookup wires and supporting components.

I usually use stock breakout-boards when I want to test a device on a breadboard. See pic. You can get them on ebay or aliexpress for next to nothing.

Yeah, I have used the same in the past.  But a dev board makes things a bit simpler to wire everything up.  There is a reason people reach for an Arduino more often than a bare IC and supporting components.  (Well technically there are many reasons, not all of them valid, but that is a different topic entirely.)

One topic I can really relate to is that there are many breakout boards that have too much PCB overhang next to the headers. This basically wastes one row of pins for nothing. Philipp, your boards are also guilty of this, see pic :).

Yeah, definitely a pet peeve of mine.  The STM32 blue pill is especially bad in this regard.

On other occasions, I have directly mounted the device in the target circuit and used a SOIC clamp for programming.

Yeah, I have one of those.  They are handy for quick one-off hacking sessions, but I wouldn't want to rely on one for a general purpose dev board.  They are slightly annoying to position properly, and can slip off if bumped.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 13, 2020, 06:57:39 pm
I will probably create my own version anyway, as my priorities are a bit different.  For one, I would rather have a narrower board that is a bit more optimized for use in a breadboard.

Ok, after consulting the datasheets more and thinking about it for a while, here is what I came up with for a dev board for the PFC154/PFS154/PFS173 16-pin ICs.  The board is sized to fit in a standard breadboard and leave room for 3 rows (cols?) of pins on each side.

There are four LEDs on PA3, PA4, PA5, and PA6 in a current sink configuration (needed because PA5 can only be open drain).  Having LEDs on PA3, PA5, and PA6 should give some blinky status while the programmer does its thing.  The LEDs are properly isolated (according the datasheet) using 10k resistors, which also double as the current limiting resistors for the LEDs.  Other than the LEDs I decided not to isolate PA3, PA5, PA6 from the programmer in this version.  I went back and forth on it, and decided to leave the isolation off for now.

PA5 also has a switch on it that can be configured to be either a reset button or a general purpose user button as desired.

I used a 2x4 programming header that matches up with the standard pinout of the eask-pdk-programmer.  The thought is that a 2x4 IDC cable can be brought over to an adapter board that plugs into the standard programmer header.  I already happen to have a suitable adapter that came with my SOIC-8 SMD clamp.  In addition to the in circuit programming pins (ICVPP, ICPCK, ICPDA, VDD, and GND) this 2x4 progamming header also has PA0, PA4, and PA7, which can be used for debugging support (i.e. UART through the programmer)

I used the same USB +5V (with cap) -> diode -> VDD (with cap) arrangement, although I am still not convinced on the proper values to use.  I have re-read the datasheet and app notes (APN004 and APN011) several times and am still not fully convinced that the 0.01uF capacitor limit applies to On-board wiring.  But values can be changed easily enough if there is an issue.

Footprints used:

I ordered 3x of them for $3.30 (free shipping) from OSHPARK, and shared it here: https://oshpark.com/shared_projects/eN9zYouf

I will release the source files after successful testing.  (I am still without ICs or programmer)

There may be additional revisions of this dev board after testing it out and using it for a while.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 16, 2020, 11:13:28 am
Just a short update on the "lite"-Version. I already received the partially populated boards about a week ago. Looks very nice so far. I chose not to populate the MCU, because I still had a few left.

Unfortunately the parts that have to be added manually are still stuck at customs in a separate shipment.. Nowadays ordering assembled PCBs is much faster than ordering only components.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 17, 2020, 04:49:46 pm
Hi,

Today I started working on PFC154 (industrial part?) and to my surprise after analyzing the READ and WRITE I found:

PFC154 program word = 14 bits, but read / write using 19 bits.

5 extra bits are attached to the beginning of every program word. Some extra bits usually are for error corrections, lets' see..

Some samples from logic analyzer reading: 14 bit data => 5 extra bits:
3FFF => 1F
0070 => 08
2F00 => 0E
0182 => 04

First try: classic Hamming ECC
Confirmation by using this web site http://www.ecs.umass.edu/ece/koren/FaultTolerantSystems/simulator/Hamming/HammingCodes.html (http://www.ecs.umass.edu/ece/koren/FaultTolerantSystems/simulator/Hamming/HammingCodes.html)
After entering the binary 14 bit values from above, website will show result attached to the end of the bistring.
=> All matching! It is a classic Hamming ECC using the standard syndrom :)

It is a bit unexpected, but it looks like the "industrial grade parts" are really having some extra features.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 17, 2020, 06:27:26 pm
Hi,

Today I started working on PFC154 (industrial part?) and to my surprise after analyzing the READ and WRITE I found:

PFC154 program word = 14 bits, but read / write using 19 bits.

5 extra bits are attached to the beginning of every program word. Some extra bits usually are for error corrections, lets' see..

Some samples from logic analyzer reading: 14 bit data => 5 extra bits:
3FFF => 1F
0070 => 08
2F00 => 0E
0182 => 04

First try: classic Hamming ECC
Confirmation by using this web site http://www.ecs.umass.edu/ece/koren/FaultTolerantSystems/simulator/Hamming/HammingCodes.html (http://www.ecs.umass.edu/ece/koren/FaultTolerantSystems/simulator/Hamming/HammingCodes.html)
After entering the binary 14 bit values from above, website will show result attached to the end of the bistring.
=> All matching! It is a classic Hamming ECC using the standard syndrom :)

It is a bit unexpected, but it looks like the "industrial grade parts" are really having some extra features.


JS

Interesting. So I guess that is a way to address potential biterorrs in their OTP. They must have seen some in-field failures.

There should be some kind of way to detect read errors. Maybe a flag in an I/O register?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on June 17, 2020, 06:51:25 pm
Today I started working on PFC154 (industrial part?) and to my surprise after analyzing the READ and WRITE I found:
Nice find, thanks for sharing.

I think more traditional bigger MCUs, like for example the STM32, also have an ECC protection for their flash. But I think their flash works on larger words, it is always accessed on something like 64 bits in parallel. So they have implemented the ECC for such a word and not for each single command. But given the more simplistic design of the PDKs, I think adding some extra bits for each command is a reasonable approach.

Do you also happen to have some PMC150 at hand to analyze?

They are available in my favorite package, SOT23-6, at LCSC. I might want to replace the PMS150C-U6 with them for some applications.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 23, 2020, 11:35:23 pm
[Original post for STM32 "mini-pill" (1/2 Blue Pill)]

...I decided to go ahead to create a bottom board...  I call this the STM32 Mini-Pill.  It is essentially 1/2 of the infamous "Blue-Pill" board...
[Original post for STM32 "mini-pill"/"blue-pill" Padauk Programmer Top Hat]

...I ended up creating a (mostly compatible) variation that is a top-hat for said boards...

It works! (First try!)

I got my STM32 mini-pill board delivered last Saturday and the Top Hat Programmer board delivered yesterday (Monday).  My big LCSC order got delivered today (Tuesday).  Feels like Christmas!

I started by soldering together the STM32 "mini-pill".  Soldering the STM32F072CBT6 was slightly challenging (I bent some pins on the first try), but everything else went on smoothly, and all the footprints worked out well.  A few places are a little tight, but manageable.  I left off R5 (1k5) because it isn't needed by the STM32F072 (it would probably be needed if using this as a generic dev board with a STM32F103xxxx).  I also left off R6 and D1 (LED connected to PC13) because they are covered up and duplicated on the top hat anyway.  Holding down the BOOT0 button while plugging it in (or while pressing the RESET button) launched the STM32 DFU bootloader successfully on the first try!

Next, I soldered together the STM32 Progammer Top Hat.  No real challenges on this one, other than a lot of cross referencing resistor and capacitor values against the schematic.  The schottky diodes are smaller than expected, but ended up being easy enough to hand solder.  Once again, all the footprints worked out well, and there was sufficient space (although a little cramped) to hand solder everything.

Finally, (after a close inspection under the magnifying lens) I soldered on the female header pins for the IC socket and connected the two halves together with male header pins.  It's a little tall with ZIF socket plugged in, but clearances on everything seem fine.

I had to change two lines in the Firmware source code to point to the correct ADC pins on this hardware revision (PA0/1 instead of PB0/1).  It was as simple as replacing ADC_CHANNEL_8 with ADC_CHANNEL_0 and ADC_CHANNEL_9 with ADC_CHANNEL_1.  Compiling the changes and uploading with the DFU utility was fairly straightforward.

Imagine my happiness when I put a PFS154 in the ZIF socket and saw the following output after running the probe command!:
Code: [Select]
>easypdkprog -v probe
Probing IC... found.
TYPE:FLASH RSP:0xAA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

Then, I uploaded the pre-compiled hello world example:
Code: [Select]
>easypdkprog -n PFS154 write Examples\helloworld_pfs154.ihx
Erasing IC... done.
Writing IC... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 4.00V ... calibration result: 7951482Hz (0x84)  done.

And started it up:
Code: [Select]
>easypdkprog -n PFS154 -r 4.0 start
Running IC (4.00V)... IC started, press [Esc] to stop.
Hello World!
Hello World!

IC stopped

I repeated the same steps for the PFS173 IC, which also worked perfectly on the first try.

THANK YOU to JS, and anyone else involved in bringing this open source programmer to life!

Now its time for the real fun to begin!

(I'll post my board design files soon)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 24, 2020, 02:42:39 am
Here's a few more pictures.

I cleaned up the board-to-board connection, and removed the unused pins on the overhanging section of the IC socket.  I kinda like leaving the overhang because it protects the otherwise exposed pins of the zif adapter.

And, yes, as expected, it also works fine with a SOIC-8 test clamp.

They haven't shipped yet, but I am still hopeful that I will get my dev boards by the end of the week which should make this a little bit cleaner still.

I also tested and verified that the PMS150C and PMS152 are probing correctly as well.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 26, 2020, 10:28:15 am
Good news. After some components were stuck for more than 2 weeks at customs, I finally received all parts for the "Lite" Easypdkprog.

Just to recap: This is a redesign of the easypdkprog with some circuit simplifications and only based on "Basic components" at the JLPCB assembly service. This means that it is possible to buy almost completely assembled PCBs directly from JLCPCB for very little money.

A few parts have to be added manually, see picture below.

[attach=4]

The fully assembled programmer is shown below. Form, fit and function are basically identical to the original one:

[attach=1]

I tested the r0 samples and found them to be functional. See list of tests below. One change from the original design was to remove the negative OPAMP supply, therefore the idle voltage of VDD and VPP is slightly larger than 0V, but that does not really have practical implications.

[attach=2]

I also looked at the load behavior of the new boost converter in more detail. The new one shows slightly more ripple when unloaded. This is not a big issue, since VPP and VDD ripple is defined by the opamp loop gain. However, it still does not look very nice and I noticed that I operate the device (FP6291) marginally. There is a slightly more expensive boost converter from TI (TPS61040) that I will probably switch to for the final version.

[attach=3]

I still have a few r0 boards including components to share, let me know if you are interested. Please note that also the MCU has to be soldered manually on the R0 board. I will prepare a r1 run for the final and then add it to the github with ordering instructions.

currently planned changes for r1:
   - Adjust USB solder screen for easier soldering - avoid solder bridge between ground pins.
   - Move components around so JLCPBC can place their mounting holes properly. (Current positions can be seen on the PCB - not optimal)
   - Possibly switch to new boost converter
   - Add a second row of headers, so it will be possible plug in SOIC14/16 break-out boards directly into the programmer.
   - remove r1.2 mark in metallization to avoid confusion.

Any additional suggestions?

Edit: All the r0 boards are gone, but if anyone is interested in an r1 board from the next order, please let me know.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 27, 2020, 09:05:12 pm
Here's a few more pictures.

I cleaned up the board-to-board connection, and removed the unused pins on the overhanging section of the IC socket.  I kinda like leaving the overhang because it protects the otherwise exposed pins of the zif adapter.

That looks like a very clean design! This should certainly be attractive for people who want to build and populate their own programmer. Maybe you should switch the two tiny diodes to larger ones, so it is still possible to work without a microscope :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 27, 2020, 09:16:36 pm
Ok, just sharing my design progress for the r1 version of the "lite" programmer with you. Please let me know what you think and if there are any proposals for changes.

I ended up changing far more than I initiatially intended.


3D rendering of current design:

[attach=3]

I designed minimum size breakout boards for all SO8 and SO16 flash variants of the Padauk MCUs. These can be plugged into the programmer for programming and can then be used on a breadboard. These should be quite convenient for prototyping. An optional LED allows quick validation of "blinky".

It turns out two different pinouts are needed to cover all types. See attached PDF for more details. The V-scoring is quite aggressive - let's see whether that works out.

[attach=1]

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 27, 2020, 10:55:03 pm
Here's a few more pictures.

I cleaned up the board-to-board connection, and removed the unused pins on the overhanging section of the IC socket.  I kinda like leaving the overhang because it protects the otherwise exposed pins of the zif adapter.

That looks like a very clean design! This should certainly be attractive for people who want to build and populate their own programmer. Maybe you should switch the two tiny diodes to larger ones, so it is still possible to work without a microscope :)

Thanks tim_!

I love the puzzle and art of pcb design.  I'm a bit jealous of being able to use 0603 or 0402 sized components, because it looks like they can really help shrink the board size further, and provide more layout options.  But, I just find them too small to be worth trying to hand solder, and I am not ready to commit to automated assembly yet.  If I make a second version of the programmer top hat, I will look into using larger sized diodes, but for now I have no use for any more programmer boards, so no incentive for a re-spin at the moment.

I did release all my design files for the STM32 "mini-pill" board.
   https://github.com/serisman/stm32-mini-pill
   https://hackaday.io/project/173350-stm32-mini-pill

I haven't yet released the design files for the programmer top hat, mostly because I haven't decided where to release them yet, and I am having too much fun using the completed programmer.   ;D

I also started my own repository to gather Padauk documentation, library files, and source code for my projects (https://github.com/serisman/Padauk).  I don't mean to compete with anything you or JS or spth have done, but I needed to get some of what I was working on checked in and backed up so it wasn't just on my hard drive.  At the very least it is a play area to try some things out slightly differently than the other repos.

This repo is still in a fairly bare state, but I did check in my source code for one full working project (a 'bare-minimum' 4-digit 7-segment digital clock) that I am pretty happy with (https://github.com/serisman/Padauk/tree/master/projects/7-seg-clock).  I don't have a write up for it yet, and it is just on a breadboard for the moment, but was a great proof of concept for the usefulness of these ultra cheap MCUs!  I'll eventually create a custom pcb for it and complete a write up.  The entire program uses less than 0.5KW of code and around 20 bytes of RAM, so it should fit on just about any Padauk MCU that has enough pins (currently using 14 IOs, so needs a 16-pin IC).  I have tested it with a PFS154-S16, but imagine it would work with no changes on a PFS173-S16 and probably even a PMS152-S16 (once we have write support available in easypdkprog).  There is a mix of mostly C code as well as a few methods with 'optimized' inline assembly.  The optimization wasn't really needed, but I wanted to get some experience with the Padauk instruction set and see how small/fast I could make some of the more 'critical' code sections.

Over half the code is just the 'UI' that allows setting the time on the clock.  There is a single button.  A short press when the HH:MM is displayed will briefly switch to show seconds.  A medium 1-2 second press will switch into config mode, where short presses will increment the currently selected time value, and medium presses will advance to the next digit, and long presses will exit config mode.

The BOM is pretty minimal: (1) PFS154-S16 ~$0.07, (1) 4-digit 7-seg 'time' display ~$0.40, (1) 74HC595 used as a digit driver ~$0.03 (cheaper than discrete transistors, and provides 4-8 outputs from 3 IOs), (1) button ~$0.02, and (1) 32.758kHz crystal with (2) 22pF caps ~$0.04.  I'm doing a few naughty things driving the 7-segment display without proper current limiting resistors or digit drivers, but it seems to work pretty good so far.  Using a second 74HC595 could free up a bunch of additional IOs, meaning this would fit on 6 IO MCUs (i.e. SOP-8), but the overall price would still be about the same, so what's the point.

Originally, I had been experimenting with this 'digital clock' with an external I2C RTC (DS1307) with plans to switch to the much cheaper BM8563/PCF8563 when parts came in.  But, then I realized if I just use the 32.768kHz crystal directly on the Padauk MCU (as input for the T16 timer interrupt), it would reduce parts count further and still be just as accurate (hopefully).  There is some library source code for a 'generic' I2C master and the DS1307 RTC that was fairly easy to implement (I didn't finish the full project so that isn't checked in yet, but the library code is there).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 27, 2020, 11:05:11 pm
I love the puzzle and art of pcb design.  I'm a bit jealous of being able to use 0603 or 0402 sized components, because it looks like they can really help shrink the board size further, and provide more layout options.  But, I just find them too small to be worth trying to hand solder, and I am not ready to commit to automated assembly yet.  If I make a second version of the programmer top hat, I will look into using larger sized diodes, but for now I have no use for any more programmer boards, so no incentive for a re-spin at the moment.

I love it too, it's almost like meditation :). You should look into the JLCPCB assembly service, it's probably much cheaper than you think.

Quote
I also started my own repository to gather Padauk documentation, library files, and source code for my projects (https://github.com/serisman/Padauk).  I don't mean to compete with anything you or JS or spth have done, but I needed to get some of what I was working on checked in and backed up so it wasn't just on my hard drive.  At the very least it is a play area to try some things out slightly differently than the other repos.

Well, I basically only have my own repository because my toolchain is a bit different from the one in the free-pdk repository. We should somehow all work together on cleaning that up and create better documentation so other people have a less steep learning curve. Maybe we could activate the Wiki on Github?

But first things first, need to finish the lite programmer before that...

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 27, 2020, 11:24:14 pm
I love the puzzle and art of pcb design.  I'm a bit jealous of being able to use 0603 or 0402 sized components, because it looks like they can really help shrink the board size further, and provide more layout options.  But, I just find them too small to be worth trying to hand solder, and I am not ready to commit to automated assembly yet.  If I make a second version of the programmer top hat, I will look into using larger sized diodes, but for now I have no use for any more programmer boards, so no incentive for a re-spin at the moment.

I love it too, it's almost like meditation :). You should look into the JLCPCB assembly service, it's probably much cheaper than you think.

Yeah, I have looked into it, and agree it is pretty cheap, especially if you can make use of their basic components and/or need more than a small handful of boards.  I just haven't thought up any projects that make sense to use it yet.

I also started my own repository to gather Padauk documentation, library files, and source code for my projects (https://github.com/serisman/Padauk).  I don't mean to compete with anything you or JS or spth have done, but I needed to get some of what I was working on checked in and backed up so it wasn't just on my hard drive.  At the very least it is a play area to try some things out slightly differently than the other repos.

Well, I basically only have my own repository because my toolchain is a bit different from the one in the free-pdk repository. We should somehow all work together on cleaning that up and create better documentation so other people have a less steep learning curve. Maybe we could activate the Wiki on Github?

Yeah, my toolchain is a bit different too.  I haven't dug too deeply into yours, but if I remember correctly it is fairly similar to mine.  I like the include files from the Examples in the easy-pdk-programmer-software repo better than the standalone nature of the sdcc-pdk-code-examples repo.  But, I still wanted to augment them further.  I added a util.h file that has helpers that I find useful.  I also structured it in a way that separates library headers and code from the projects.  Each project has it's own build directory and Makefile where options can be tweaked.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 27, 2020, 11:25:36 pm
JS,

FYI... I just submitted a Pull Request (https://github.com/free-pdk/easy-pdk-programmer-software/pull/25) for adding preliminary support for PMS152 as well as fixed a few bugs that I found after researching the datasheets and Padauk IDE files.  I tried to write a PMS152, after un-commenting the appropriate code in fpdkicdata.c and re-compiling easypdkprog.  It seemed to mostly write correctly, but failed on calibration, and when read back, there are a few differences.  So, it may require some more code changes in easypdkprog before it is fully supported.  I already wasted two ICs before deciding to stop until someone more familiar with the code could take a look.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on June 28, 2020, 04:59:14 pm
  • I added a second pin header to allow plugging in wide breakout boards. More about this below. Unfortunately this means that the programmer will not fit into JS casing anymore without using a hacksaw... Let me know if you think this is a bad idea.
I think different widths are a good idea. I personally don't think breakout boards are worth it (especially for the OTP types), but some people may prefer to work that way.

I think different widths are more interesting to fit different kinds of IC sockets, so sourcing fitting ones becomes easier. Currently you need ones with 7.62mm spacing, but some seem to me like they have 10.16mm spacing:
https://www.aliexpress.com/item/1107288077.html (https://www.aliexpress.com/item/1107288077.html)

I think you'd have to add another row for them, but that shouldn't be a problem.

As the case is 3d printed, I don't think it is an issue to change it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 28, 2020, 09:22:02 pm
JS,

FYI... I just submitted a Pull Request (https://github.com/free-pdk/easy-pdk-programmer-software/pull/25) for adding preliminary support for PMS152 as well as fixed a few bugs that I found after researching the datasheets and Padauk IDE files.  I tried to write a PMS152, after un-commenting the appropriate code in fpdkicdata.c and re-compiling easypdkprog.  It seemed to mostly write correctly, but failed on calibration, and when read back, there are a few differences.  So, it may require some more code changes in easypdkprog before it is fully supported.  I already wasted two ICs before deciding to stop until someone more familiar with the code could take a look.

Hi,

Writing of PMS152 was never tested from me. I just copied some values around to have place holders. A capture with logic analyzer is needed to reveal full details.

=> Do you still have the exact same hex file you wrote and a read back from the IC?


Until now there was no demand for PMS152 so it was pushed back on my list.

But, since you really try to develop something for this IC and you also open sourced your project I'm more than motivated to put PMS152 on top of the list now  :)

I had a brief look at your PMS152.h and it looks good. 
Some things I noticed:
- it looks like you used the main branch as source since some of the unknown ROP defines are already deciphered and in development branch (see PFS173.h).
- you should try the H9 and L9 macro for IHRC/ILRC calibration since it might be that PADIER needs to be set explicit in order to get input (development branch has H9/L9 macros and easypdkprog has calibration code for H9/L9 14 bit).

=> You also should target your pull requests to the development branch.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 28, 2020, 09:36:00 pm
JS,

FYI... I just submitted a Pull Request (https://github.com/free-pdk/easy-pdk-programmer-software/pull/25) for adding preliminary support for PMS152 as well as fixed a few bugs that I found after researching the datasheets and Padauk IDE files.  I tried to write a PMS152, after un-commenting the appropriate code in fpdkicdata.c and re-compiling easypdkprog.  It seemed to mostly write correctly, but failed on calibration, and when read back, there are a few differences.  So, it may require some more code changes in easypdkprog before it is fully supported.  I already wasted two ICs before deciding to stop until someone more familiar with the code could take a look.

Hi,

Writing of PMS152 was never tested from me. I just copied some values around to have place holders. A capture with logic analyzer is needed to reveal full details.

=> Do you still have the exact same hex file you wrote and a read back from the IC?


Until now there was no demand for PMS152 so it was pushed back on my list.

But, since you really try to develop something for this IC and you also open sourced your project I'm more than motivated to put PMS152 on top of the list now  :)

I had a brief look at your PMS152.h and it looks good. 
Some things I noticed:
- it looks like you used the main branch as source since some of the unknown ROP defines are already deciphered and in development branch (see PFS173.h).
- you should try the H9 and L9 macro for IHRC/ILRC calibration since it might be that PADIER needs to be set explicit in order to get input (development branch has H9/L9 macros and easypdkprog has calibration code for H9/L9 14 bit).

=> You also should target your pull requests to the development branch.

JS

Thanks for your response JS,

I'm not sure if you read through the related GitHub issue, but some of this is answered there: https://github.com/free-pdk/easy-pdk-programmer-software/issues/26

I did make a test after setting PADIER (right before the calibration call) and it didn't seem to make any difference.

I do still have the exact same .bin files wrote/read if they are helpful, but I don't think the issue with with writing the IC at this point.

I just re-targeted my "mini-pill" Pull Request to the development branch (https://github.com/free-pdk/easy-pdk-programmer-software/pull/24).  It was cleanly able to be moved from master to development.

I will re-target the PMS152 one to the development branch in an hour or so.  I think I might need to do some merging on that one (and I'm unavailable for the next 40 minutes).

Thanks again for all your hard work on these ultra cheap MCUs!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 29, 2020, 12:07:37 am
=> You also should target your pull requests to the development branch.

JS,

I re-targeted my pull request to the development branch, re-applied my mini-pill changes, re-build and uploaded the new 1.3 firmware, and re-compiled easypdkprog.  But now I can't even probe OTP ICs (I tried both PMS150C and PMS152).  Flash based ICs still seem fine (I can probe/erase/write/read to both PFS154 and PFS173).  So, it seems like OTP support may be broken right now in the development branch.  Can you duplicate this on your end?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 29, 2020, 01:12:21 am
JS,

I re-targeted my pull request to the development branch, re-applied my mini-pill changes, re-build and uploaded the new 1.3 firmware, and re-compiled easypdkprog.  But now I can't even probe OTP ICs (I tried both PMS150C and PMS152).  Flash based ICs still seem fine (I can probe/erase/write/read to both PFS154 and PFS173).  So, it seems like OTP support may be broken right now in the development branch.  Can you duplicate this on your end?

Ok, false alarm.  I was missing your flash type fix from yesterday.  Once I found and brought that fix over, OTP probe is working again.

EDIT: Writing to PMS152 (including calibration) now works too!

Code: [Select]
>easypdkprog -n PMS152 write Examples\helloworld_pms152.ihx
Writing IC (186 words)... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 4.00V ... calibration result: 8006747Hz (0x4E)  done.

Code: [Select]
>easypdkprog -n PMS152 -r 4.0 start
Running IC (4.00V)... IC started, press [Esc] to stop.
Hello World!
Hello World!

IC stopped

It looks like PMS152 DOES need the PADIER fix like the PFS173.  I'll update the pms152.h include file appropriately.  I think when I tested this earlier I accidentally used the old .ihx file and didn't actually test the PADIER fix.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 29, 2020, 01:40:21 am
- you should try the H9 and L9 macro for IHRC/ILRC calibration since it might be that PADIER needs to be set explicit in order to get input (development branch has H9/L9 macros and easypdkprog has calibration code for H9/L9 14 bit).

JS,

It looks like the 14 bit version is H10, not H9, and there is not yet a L10 equivalent.  Does that seem correct?  If so, I can add the L10 equivalent.  Looks like we need a new equivalent of B1A for bandgap calibration as well.

Also, it looks like H10 starts off at 0x00 instead of 0xFF, meaning the first measured value is 0x01 instead of 0x00.  Doesn't that mean the calibration value will also be off by one (or is that tweaked elsewhere)?

I'm wondering if we would be better off getting SDCC to add the PADIER=0xFF (and any other needed default overrides) as part of the initialization code so we don't have to have so many different calibration routines, and our programs can then rely on the same defaults across MCUs as well.  I think the Padauk IDE already does it this way.  Maybe if SDCC can't/shouldn't do it, we can find a way to insert it in the IC specific .h include files.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 29, 2020, 07:01:14 am
  • I added a second pin header to allow plugging in wide breakout boards. More about this below. Unfortunately this means that the programmer will not fit into JS casing anymore without using a hacksaw... Let me know if you think this is a bad idea.
I think different widths are a good idea. I personally don't think breakout boards are worth it (especially for the OTP types), but some people may prefer to work that way.

I think different widths are more interesting to fit different kinds of IC sockets, so sourcing fitting ones becomes easier. Currently you need ones with 7.62mm spacing, but some seem to me like they have 10.16mm spacing:
https://www.aliexpress.com/item/1107288077.html (https://www.aliexpress.com/item/1107288077.html)

I think you'd have to add another row for them, but that shouldn't be a problem.

As the case is 3d printed, I don't think it is an issue to change it.

Thank you for your feedback! Yes, the breakout boards only make sense for the flash types.

I know that socket, I use it for the OTP variants :) It fits into the current DIP16 spacing, so no additional header would be needed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 29, 2020, 10:12:29 am
- you should try the H9 and L9 macro for IHRC/ILRC calibration since it might be that PADIER needs to be set explicit in order to get input (development branch has H9/L9 macros and easypdkprog has calibration code for H9/L9 14 bit).

JS,

It looks like the 14 bit version is H10, not H9, and there is not yet a L10 equivalent.  Does that seem correct?  If so, I can add the L10 equivalent.  Looks like we need a new equivalent of B1A for bandgap calibration as well.

Also, it looks like H10 starts off at 0x00 instead of 0xFF, meaning the first measured value is 0x01 instead of 0x00.  Doesn't that mean the calibration value will also be off by one (or is that tweaked elsewhere)?

I'm wondering if we would be better off getting SDCC to add the PADIER=0xFF (and any other needed default overrides) as part of the initialization code so we don't have to have so many different calibration routines, and our programs can then rely on the same defaults across MCUs as well.  I think the Padauk IDE already does it this way.  Maybe if SDCC can't/shouldn't do it, we can find a way to insert it in the IC specific .h include files.

Hi,

during development for PFS173 I found that we need the PADIER for some ICs ==> I created the 9 (9 instructions) variant
during development for PFS172 I found that using a value of 0xFF in IHRCR locked up the IC so I created the 10 variant (1 more instruction to start with 0 - the new offset is respected in calibration)
ILRC and BG calibration always worked with any value (no 10 variant needed)

I think we should rework calibration to use the "works for all" 10 version for all IC variants, even if it "wastes" 2 instructions in code memory on some ICs.

I also plan to make a more generic calibration routine so we can specify the location of ILRCR and BGTR register as a parameter in tuning macro.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 29, 2020, 04:30:52 pm
during development for PFS172 I found that using a value of 0xFF in IHRCR locked up the IC so I created the 10 variant (1 more instruction to start with 0 - the new offset is respected in calibration)

I think we should rework calibration to use the "works for all" 10 version for all IC variants, even if it "wastes" 2 instructions in code memory on some ICs.

I agree.

Setting PADIER in all cases seems like a good idea, even if most ICs default it on reset at the hardware level.

And, I really like the idea of starting calibration at the lowest frequency and working our way up, instead of briefly using the max (technically unsupported?) frequency and then only switching to the lowest frequency after detecting a pulse on PA4.

I also plan to make a more generic calibration routine so we can specify the location of ILRCR and BGTR register as a parameter in tuning macro.

Yeah, that sounds even better.  Might want to allow setting the locations of all the registers (PAC, PA, PADIER, IHRCR, ILRCR, BGTR, etc...) so we only have one algorithm per calibration type.
Title: Using bitfield in PDK14 SDCC -> Bug
Post by: tim_ on June 29, 2020, 11:30:13 pm
I have been trying again to use bitfields in SDCC to ease port access. There is still a bug, where SDCC generates incorrect code.

I will also submit a ticket to SDCC.

Example code (Blinky):

Code: [Select]
struct PORT_bits
{
uint8_t p0:1;
uint8_t p1:1;
uint8_t p2:1;
uint8_t p3:1;
uint8_t p4:1;
uint8_t p5:1;
uint8_t p6:1;
uint8_t p7:1;
}; // __attribute__((__packed__));

#define BF_PA   (*(volatile struct PORT_bits *)&PA)

void main(void)
{
  PAC |= _BV(LEDPIN);     // This syntex will infer set0/set1

  for (;;) {
BF_PA.p0=1;

  // PA ^= _BV(LEDPIN); // Toggle LED
delay_ms(500);
BF_PA.p0=0;
delay_ms(500);
  }
}

SDCC version:

Code: [Select]
SDCC : gbz80/tlcs90/z80n/pic14/ds400/pdk13/pdk14/pdk15 4.0.2 #11683 (Linux)

Here is what is emitted:
Code: [Select]
                                    260 ; bitfields.c: 55: BF_PA.p0=1;
      000040 01 2F                  261 mov a, #0x01
a     000042                        262 or _pa+0, a

...

      00004C FE 2F                  270 mov a, #0xfe
a     00004E                        271 and _pa+0, a

"AND io,a" and  "OR io,a" unfortunately do not exist. Therefore the assembler fails to assemble this. This needs to be replaced with set0 / set1.

Edit:

Once this works in SDCC it would be a very useful way to augment the port defines, because it will be possible to set single bits with direct assignments like "PA7=1", a direct equivalent to the machine instruction, instead of messing around with bitmasks. I use this all the time on AVR with AVR-GCC and it works very well. AVR-GCC generates very efficient code out of this.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 03:45:22 am
I got my dev boards in the mail today, and soldered one up with a PFS173-S16 this evening.  I'll build another one with a PFS154-S16 later.

[attach=1] [attach=2]

For the most part it works great and simplifies development a bit.

[attach=3]

I did have to change the resistor on PA6 to 22k (instead of the 10k that the PA3,PA4,PA5 are able to use) in order to actually successfully program the IC through the header.  The datasheet seems to indicate that 10k is all the isolation that's needed, but the characteristics of the easy-pdk-programmer must be different.  Maybe the timing could be adjust to compensate?  I'm not sure why the other pins seem fine with 'only' 10k resistors though.

The other 'issue' I noticed is that the programmer appears to be pulling PA5 low while it is connected, even while it is idle.  This makes the code think that the button is always pressed (and the PA5 LED is always lit up).  If the programmer is disconnected, it works properly.  I think the programmer is trying to idle (i.e. high-z) the line, but the op-amp is pulling it low.  I reported this as an issue in GitHub, but I'm not sure if anything can or will be done about it.  Possibly the easiest solution would be to allow the programmer to idle the PA5/VPP line high (maybe through an extra command line option with easypdkprog?).

I originally planned to use a 2x4 male IDC connector with an IDC cable back to the programmer, but had previously created two 1x4 cables for easier breadboarding, so instead choose to install a 2x4 female connector.  But, this could easily be change to a different connector as needed.

I whipped up an example program that makes use of the on-board LEDs and BTN.
Here is the obligatory blink example: https://github.com/serisman/Padauk/tree/master/examples/blink
- LEDs 1 and 2 (PA3 , PA4) alternate every quarter second or so.
- LED 3 (PA6) will light up whenever the button (PA5) is pressed.
- LED 4 (PA5) will also light up when the button is pressed as it shares a pin with the button.

[attach=4]

I will share the design files somewhere if there is any actual interest from anyone for them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 30, 2020, 05:38:48 am
I got my dev boards in the mail today, and soldered one up with a PFS173-S16 this evening.  I'll build another one with a PFS154-S16 later.
Nice! I like the pin descriptions.
Quote
I did have to change the resistor on PA6 to 22k (instead of the 10k that the PA3,PA4,PA5 are able to use) in order to actually successfully program the IC through the header.  The datasheet seems to indicate that 10k is all the isolation that's needed, but the characteristics of the easy-pdk-programmer must be different.  Maybe the timing could be adjust to compensate?  I'm not sure why the other pins seem fine with 'only' 10k resistors though.
The original programmer probably uses a bus driver to convert the logic levels to ones that are consistent with VDD of the device. That should improve noise immunity a bit.

Quote
The other 'issue' I noticed is that the programmer appears to be pulling PA5 low while it is connected, even while it is idle.  This makes the code think that the button is always pressed (and the PA5 LED is always lit up).  If the programmer is disconnected, it works properly.  I think the programmer is trying to idle (i.e. high-z) the line, but the op-amp is pulling it low.  I reported this as an issue in GitHub, but I'm not sure if anything can or
will be done about it.  Possibly the easiest solution would be to allow the programmer to idle the PA5/VPP line high (maybe through an extra command line option with easypdkprog?).

VPP is always connected to ground by a ~25 kOhm resistor due to the two voltage dividers that are used as feedback. So it is not possible to let it float. 

Quote
I whipped up an example program that makes use of the on-board LEDs and BTN.

Code: [Select]
setPinOutput(PIN_LED2);
Do we really have to copy the Arduino style? With bitfields (see above) we could directly turn individual pins into variables so you can write e.g. PA5=1;. The compiler should be able to generated optimal code once fixed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 06:01:01 am
Code: [Select]
setPinOutput(PIN_LED2);
Do we really have to copy the Arduino style? With bitfields (see above) we could directly turn individual pins into variables so you can write e.g. PA5=1;. The compiler should be able to generated optimal code once fixed.

We, of course don't have to do anything.  ;)  That code is easily changeable if/when something better is available.

If you don't like that, don't look at some of the more recent updates I just pushed.  >:D

Behind the scenes, 'setPinOutput(PIN_LED2)' is just calling a macro that ultimately does: 'PAC |= (1<<4)'.  The macro makes it cleaner/easier to read and makes it easier to swap pins around just by changing one #define at the top of the file (or passing in an override from the command line or Makefile).

Of all the things to dislike about Arduino, is the cleanliness/readability really one of them?  There is a reason that Arduino is so popular.  If we want more adoption, we'll need to lower the barrier to entry across the board, and having code environments that look a bit more similar to what a lot of people already know could help with that.  I might even change my repo name to be Pdkuino and try and cater to more of that audience.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 30, 2020, 06:39:40 am
Code: [Select]
setPinOutput(PIN_LED2);We, of course don't have to do anything.  ;)  That code is easily changeable if/when something better is available.

If you don't like that, don't look at some of the more recent updates I just pushed.  >:D

You mean "setup()" and "main()"? Well ... :)

Of course an optional Arduino-like include could not hurt.

But I was thinking there is a lack of consistency in the general toolchains that exist around PDK. It would be good to have at least one point of reference that we can all agree on extending on together. (olbigatory: https://xkcd.com/927/)

There are now at least 4 different repositories that have examples sitting somewhere in a deeply nested folder. All of them based on a different set of system includes. But as someone wanting to start development, it is simply a pain to find somethign that is consistent.

For example, there are still glaring issues when trying to use "printf" (Some of the examples use "puts" for a reason) . I implemented some optimized routines that took a lot of effort, to be at least able to do basic printf-style debugging (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/PDK_softuart.c), but there is simply no place to put them oither than my own repositiy.

I also still don't know how to build a librariy with conditional linking of functions to be able to cope with the limited program memory.

Could we agree on starting a new repository on "free-pdk" that contains a central repository for the toolchain and examples? (Also looking at JS and Phillipp)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 07:17:54 am
Code: [Select]
setPinOutput(PIN_LED2);We, of course don't have to do anything.  ;)  That code is easily changeable if/when something better is available.

If you don't like that, don't look at some of the more recent updates I just pushed.  >:D

You mean "setup()" and "main()"? Well ... :)


Yep, I was referring to the #include "pdkuino.h" at the top that moves main() out of the main .c file and assumes you will instead implement setup() and loop() methods.   >:D

Of course an optional Arduino-like include could not hurt.

But I was thinking there is a lack of consistency in the general toolchains that exist around PDK. It would be good to have at least one point of reference that we can all agree on extending on together. (olbigatory: https://xkcd.com/927/)

There are now at least 4 different repositories that have examples sitting somewhere in a deeply nested folder. All of them based on a different set of system includes. But as someone wanting to start development, it is simply a pain to find somethign that is consistent.


I agree.  But we aren't there yet.  I did start working on a refactoring of the include files on a branch in the easy-pdk-programmer-software repo earlier today, with a goal of trying to clean it up a bit, make it more extensible, and separate out the easy-pdk specific code from the more general pdk stuff that maybe could eventually be packaged into SDCC.  If you have a chance, take a look and provide feedback on the (work-in-progress) pull request: https://github.com/free-pdk/easy-pdk-programmer-software/pull/33.  Please keep in mind this isn't 'finished' or 'ready to use' yet, and maybe not all the ideas I was playing around with are good ideas, so please be gentle.  ;D

Even if I do go the pdkuino route with my repo, it would ideally just be a layer on top of the base pdk include files, not a replacement for them.

For example, there are still glaring issues when trying to use "printf" (Some of the examples use "puts" for a reason) . I implemented some optimized routines that took a lot of effort, to be at least able to do basic printf-style debugging (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/PDK_softuart.c), but there is simply no place to put them oither than my own repositiy.

I also still don't know how to build a librariy with conditional linking of functions to be able to cope with the limited program memory.

Yeah, the limited resources are definitely something we have to find a way to manage.  I haven't tried to use printf-style debugging yet, mostly because I assumed it would be too resource intensive.  For the things I have been playing around with so far, a logic analyzer is actually more useful anyway.

For SDCC, the only way I have found for it to have conditional linking (or exclusion of unused functions) is if each one is in it's own file and compiled into a library.  I think the SDCC manual mentions that somewhere.  My toolchain is setup in this fashion, although it's hard to see it working since I only have one library file checked in so far.

Could we agree on starting a new repository on "free-pdk" that contains a central repository for the toolchain and examples? (Also looking at JS and Phillipp)

I personally don't have access to the free-pdk repos to start something like that, but would be happy to collaborate there if that was setup.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 07:34:45 am
I got my dev boards in the mail today, and soldered one up with a PFS173-S16 this evening.  I'll build another one with a PFS154-S16 later.

I built up another one, this time with a PFS154-S16 and a 2x4 IDC connector.

[attach=1] [attach=2]

I used 22k resistors for all the LEDs on this one, but for some reason I can't program it at all with any resistor on the PA6 pin (I also tried 33k and 47k).  It could be that the IDC cable has higher resistance, or maybe the PFS154 is more sensitive than the PFS173, or maybe using 22k instead of 10k resistors on the other pins is affecting it in some way.  I'll have to do more testing later, but just taking the one resistor off makes it work again (although the LED won't work without it).

I think I like this IDC connector version better after all.  It is a bit easier to connect/disconnect and a bit lower profile.

[attach=3]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 30, 2020, 07:35:33 am
I agree.  But we aren't there yet.  I did start working on a refactoring of the include files on a branch in the easy-pdk-programmer-software repo earlier today, with a goal of trying to clean it up a bit, make it more extensible, and separate out the easy-pdk specific code from the more general pdk stuff that maybe could eventually be packaged into SDCC.  If you have a chance, take a look and provide feedback on the (work-in-progress) pull request: https://github.com/free-pdk/easy-pdk-programmer-software/pull/33.  Please keep in mind this isn't 'finished' or 'ready to use' yet, and maybe not all the ideas I was playing around with are good ideas, so please be gentle.  ;D

Even if I do go the pdkuino route with my repo, it would ideally just be a layer on top of the base pdk include files, not a replacement for them.
Sounds reasonable

Quote
For example, there are still glaring issues when trying to use "printf" (Some of the examples use "puts" for a reason) . I implemented some optimized routines that took a lot of effort, to be at least able to do basic printf-style debugging (https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/PDK_softuart.c), but there is simply no place to put them oither than my own repositiy.

I also still don't know how to build a librariy with conditional linking of functions to be able to cope with the limited program memory.

Yeah, the limited resources are definitely something we have to find a way to manage.  I haven't tried to use printf-style debugging yet, mostly because I assumed it would be too resource intensive.  For the things I have been playing around with so far, a logic analyzer is actually more useful anyway.

For SDCC, the only way I have found for it to have conditional linking (or exclusion of unused functions) is if each one is in it's own file and compiled into a library.  I think the SDCC manual mentions that somewhere.  My toolchain is setup in this fashion, although it's hard to see it working since I only have one library file checked in so far.

Ah, I have to look into this. This requires careful planning of the overall structure.

Quote
Could we agree on starting a new repository on "free-pdk" that contains a central repository for the toolchain and examples? (Also looking at JS and Phillipp)

I personally don't have access to the free-pdk repos to start something like that, but would be happy to collaborate there if that was setup.

Perfect :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 30, 2020, 07:39:36 am
Quote
I used 22k resistors for all the LEDs on this one, but for some reason I can't program it at all with any resistor on the PA6 pin (I also tried 33k and 47k).  It could be that the IDC cable has higher resistance, or maybe the PFS154 is more sensitive than the PFS173, or maybe using 22k instead of 10k resistors on the other pins is affecting it in some way.  I'll have to do more testing later, but just taking the one resistor off makes it work again (although the LED won't work without it).
(Attachment)

Have you looked at the voltage levels on PA6 with a scope? Btw, is your resistor pulling up or down?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 07:43:43 am
Quote
I used 22k resistors for all the LEDs on this one, but for some reason I can't program it at all with any resistor on the PA6 pin (I also tried 33k and 47k).  It could be that the IDC cable has higher resistance, or maybe the PFS154 is more sensitive than the PFS173, or maybe using 22k instead of 10k resistors on the other pins is affecting it in some way.  I'll have to do more testing later, but just taking the one resistor off makes it work again (although the LED won't work without it).
(Attachment)

Have you looked at the voltage levels on PA6 with a scope? Btw, is your resistor pulling up or down?

I haven't.  I probably need a new scope.  Mine is ancient (a really old Tektronix 2213A - 60MHz analog crt scope) and kind of a pain to use.  I've been thinking about getting a newer digital storage scope for a while now.  Have any recommendations for a reasonable one?

The resistors are pull-up.

[attach=1]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on June 30, 2020, 07:59:52 am
Quote
I used 22k resistors for all the LEDs on this one, but for some reason I can't program it at all with any resistor on the PA6 pin (I also tried 33k and 47k).  It could be that the IDC cable has higher resistance, or maybe the PFS154 is more sensitive than the PFS173, or maybe using 22k instead of 10k resistors on the other pins is affecting it in some way.  I'll have to do more testing later, but just taking the one resistor off makes it work again (although the LED won't work without it).
(Attachment)

Have you looked at the voltage levels on PA6 with a scope? Btw, is your resistor pulling up or down?

I haven't.  I probably need a new scope.  Mine is ancient (a really old Tektronix 2213A - 60MHz analog crt scope) and kind of a pain to use.  I've been thinking about getting a newer digital storage scope for a while now.  Have any recommendations for a reasonable one?

The resistors are pull-up.

(Attachment Link)

Hm... the combination of pull-up (your board) and pull-down on PA5 (programmer) will surely lead to an undefined potential between GND and VDD. The impedance on PA6 should be high enough, though. No obvious reason why it would not work?

Edit: Regarding scope: I have been happy enough with lower end Rigol. I will receive a new MSO5074 in a few days, I hope it's worth the investment.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on June 30, 2020, 01:55:29 pm
I just like to express my appreciation of you guys spurring each other on to improvements and simplifications. I hope to join the party one of these months.  :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on June 30, 2020, 06:25:11 pm
Hello!

I made an 8 pins Padauk micro breakout board. I want to share my design with you guys so you guys can use it. It was designed with EasyPDK programmer in mind.

preview: https://imgur.com/a/12QWAbP

https://easyeda.com/LovelyA72/ezpdk8
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 06:27:20 pm
Hm... the combination of pull-up (your board) and pull-down on PA5 (programmer) will surely lead to an undefined potential between GND and VDD. The impedance on PA6 should be high enough, though. No obvious reason why it would not work?

I'm actually thinking I might spin a new version of the board that uses a CD4053 (3x 2-channel analog mutiplexer/demultiplexer) to provide 2-way disconnection of PA3 (ICPCK), PA5 (ICVPP), and PA6 (ICPDA).  It would probably be controlled by a switch/button.  So, in idle state, the PA3/5/6 MCU pins would only be connected to the board header pins, but when pressed the PA3/5/6 MCU pins would only be connected to the programmer.  That would still leave GND, VDD, PA0, PA4, PA7 connected to the programmer full time, which I think means we can still 'run' the program from the programmer and perform Tx/Rx.  The real challenge is fitting the CD4053 on the board without growing it too much.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on June 30, 2020, 06:32:16 pm
I made an 8 pins Padauk micro breakout board. I want to share my design with you guys so you guys can use it.

https://easyeda.com/LovelyA72/ezpdk8

Thanks for sharing.  It looks pretty basic, the only additional component appears to be a bypass capacitor.  Can you explain your thoughts on why you prefer this over just using a generic SOP-8/16 adapter PCB or SOP-8/16 ZIF socket to DIP8/16 adapter?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on June 30, 2020, 06:36:36 pm
I made an 8 pins Padauk micro breakout board. I want to share my design with you guys so you guys can use it.

https://easyeda.com/LovelyA72/ezpdk8

Thanks for sharing.  It looks pretty basic, the only additional component appears to be a bypass capacitor.  Can you explain your thoughts on why you prefer this over just using a generic SOP-8/16 adapter PCB or SOP-8/16 ZIF socket to DIP8/16 adapter?
It acts as an adapter board between SOP and DIP. Also, since most of the padauk micros are OTP, I can write the name of the program on the board with a sharpie(white silkscreen area). It also marks the pinout for the chip to make the chip more convenient to work with.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 01, 2020, 07:38:01 pm
I also built the free-pdk programmer and started to learn Padauk microcontroller. I finished reading PFS154 datasheet and SDCC manual.
A few parts are pretty challenging for beginners, for example the calibration..., it took me almost a whole day to figure out how the hello world program works.  :phew:

This was the most diifficult hello world code I've ever seen :)
Code: [Select]
ihrcr = *((const unsigned char*)(0x87ed)); // took me hours to find where from the 0x8000 comes
https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/hello-s16/hello.c

I don't complain, I am very happy to find this topic, you guys made excellent job.

Anyway I am not sure for beginners it is a good idea to start with SDCC. Are there any pure assembler available for this MCU for those who don't want to buy the Padauk programmer?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 01, 2020, 07:42:44 pm
I also built the free-pdk programmer and started to learn Padauk microcontroller. I finished reading PFS154 datasheet and SDCC manual.
A few parts are pretty challenging for beginners, for example the calibration..., it took me almost a whole day to figure out how the hello world program works.  :phew:

This was the most diifficult hello world code I've ever seen :)
Code: [Select]
ihrcr = *((const unsigned char*)(0x87ed)); // took me hours to find where from the 0x8000 comes
https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/hello-s16/hello.c

I don't complain, I am very happy to find this topic, you guys made excellent job.

Anyway I am not sure for beginners it is a good idea to start with SDCC. Are there any pure assembler available for this MCU for those who don't want to buy the Padauk programmer?

Have you seen the Examples directory in the easy-pdk-programmer-software repo?

e.g. https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/helloworld.c

At the very least, there are macros for easier calibration and defines for registers and their values.

Work is underway to try and standardize include files and example programs: (e.g. https://github.com/free-pdk/easy-pdk-programmer-software/pull/33)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 01, 2020, 07:46:19 pm
Anyway I am not sure for beginners it is a good idea to start with SDCC. Are there any pure assembler available for this MCU for those who don't want to buy the Padauk programmer?

Well, there are the assemblers that come with SDCC…
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 02, 2020, 12:20:35 am
I have published some i2c slave code examples for PFS154/PMC150C:

https://github.com/kaweksl/pdk-codebucket
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 02, 2020, 03:06:20 am
Hi!
I opened a pull request at https://github.com/free-pdk/free-pdk.github.io/pull/2
This is a basic responsive improvement on the website and it makes the website mobile friendly.
Before:
(https://user-images.githubusercontent.com/37679684/86285128-13dc5100-bbb2-11ea-8024-daf2d9ae7b7f.png)

After:
(https://user-images.githubusercontent.com/37679684/86285113-0aeb7f80-bbb2-11ea-9d0e-43196925759f.png)

thank you!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 02, 2020, 04:14:53 am
Work is underway to try and standardize include files and example programs: (e.g. https://github.com/free-pdk/easy-pdk-programmer-software/pull/33)

JS, spth, tim_, and others...

I have just completed a major refactoring of the include files (and Examples) from the easy-pdk-programmer-software repo, and am asking for community review as this point.
https://github.com/free-pdk/easy-pdk-programmer-software/pull/33

The goals as stated in the pull request are:

(https://imgs.xkcd.com/comics/standards.png)

Here is an overview of the changes introduced and the directory structure:
The easy-pdk/ directory contains things that are specific to the easy-pdk-programmer including:

The pdk/ directory contains things that are programmer agnostic (i.e. don't assume or require the easy-pdk-programmer)

I included support for the following devices:

Let me know if there are other devices people would like to see included out of the gate.  It is easier to define new devices than before.

One final note... the calibration routines rely on the not yet released feature/newcalibration code that JS has finished up but not yet merged to development branch.  So, testing anything to do with calibration will require pulling down that branch and rebuilding both the firmware and easypdkprog software.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 02, 2020, 04:22:33 am
I have published some i2c slave code examples for PFS154/PMC150C:

https://github.com/kaweksl/pdk-codebucket

Excellent!  Thanks for posting that.

I'll have to check it out later.  i2c slave is definitely on my list of things to try with these ICs.

What kind of i2c speed are you able to achieve?

EDIT:  Those peephole rules look really useful.  I wasn't even aware you could do that with SDCC.  Maybe I'll be able to stop writing inline assembly now!  I wonder what it would take to get SDCC to perform these optimizations by default?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: eliocor on July 02, 2020, 08:15:59 am
OT: what program was used for creating this type of image?
 
(https://free-pdk.github.io/images/PFS154_S14.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 02, 2020, 09:49:25 am
EDIT:  Those peephole rules look really useful.  I wasn't even aware you could do that with SDCC.  Maybe I'll be able to stop writing inline assembly now!  I wonder what it would take to get SDCC to perform these optimizations by default?

These rules can't be just added to the rules SDCC applies by default (see sdcc/src/pdk/peeph.def), as in general, they can break stuff. Consider .e.g.

Code: [Select]
volatile unsigned char c;

void f(void)
{
c |= 0x04;
}

The peephole rules from https://github.com/kaweksl/pdk-codebucket/blob/master/peephole_rules/peephole_pdk14.def will "optimize" that into a use of set1. However, the address of c is not known until later at link time. The linker might decide to place c in the upper half of the address space, while set1 only works on the lower half of the address space.

There would be ways to make better use of set1 in SDCC, but it's a bit more complex (involves changes in register allocation, code generation and fixing https://sourceforge.net/p/sdcc/bugs/3075/ (https://sourceforge.net/p/sdcc/bugs/3075/)); I hope to have something working for I/O by the end of the week.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 02, 2020, 11:33:40 am
What kind of i2c speed are you able to achieve?

100kHz only, at 400kHz interrupt fires to late, maybe it could be achieved with constant pulling. Some day i will try make 400kHz address sampling and for rest I would use clock stretching.


The peephole rules from https://github.com/kaweksl/pdk-codebucket/blob/master/peephole_rules/peephole_pdk14.def will "optimize" that into a use of set1. However, the address of c is not known until later at link time. The linker might decide to place c in the upper half of the address space, while set1 only works on the lower half of the address space.

There would be ways to make better use of set1 in SDCC, but it's a bit more complex (involves changes in register allocation, code generation and fixing https://sourceforge.net/p/sdcc/bugs/3075/ (https://sourceforge.net/p/sdcc/bugs/3075/)); I hope to have something working for I/O by the end of the week.


I agree, they can't be placed into sdcc general rules, because of that addressing issue. In code i made a comment about this.
Also assembler gonna complain about not being able to address operations.

Maybe implement in SDCC some keyword (like 'volatile') that would mark variable as bit accessible, then compiler could name this variable differently, so it could be targeted as pattern, linker could also place them at beginning of memory too.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 02, 2020, 12:24:28 pm
There would be ways to make better use of set1 in SDCC, but it's a bit more complex (involves changes in register allocation, code generation and fixing https://sourceforge.net/p/sdcc/bugs/3075/ (https://sourceforge.net/p/sdcc/bugs/3075/)); I hope to have something working for I/O by the end of the week.

Bit / reset instructions are working for I/O in SDCC 4.0.2 #11707 now. Implementing it for memory would be a lot of effort for little gain, so it probably won't be done anytime soon.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 02, 2020, 10:01:18 pm
OT: what program was used for creating this type of image?
 
(https://free-pdk.github.io/images/PFS154_S14.png)

Affinity Designer should do the job. It's a nice software, and I am using it for my design works.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 03:27:33 am
Bit / reset instructions are working for I/O in SDCC 4.0.2 #11707 now.
Oh, that's interesting.   :-+  Does this mean that we can use __bit now (or even bitfields), or just that SDCC will choose to generate more set0/set1 instructions for more case?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 03:30:15 am
What kind of i2c speed are you able to achieve?

100kHz only, at 400kHz interrupt fires to late, maybe it could be achieved with constant pulling. Some day i will try make 400kHz address sampling and for rest I would use clock stretching.


Still, 100kHz is nothing to sneeze at.  That still puts it neck and neck with lots of other dedicated ICs out there.  :-+  Have you tried variable frequencies between 100 kHz and 400 kHz to see where it starts breaking down?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 03:38:15 am
spth,

I noticed when I was trying to optimize some of the code examples (specifically the adctest.c example) that certain functions that I am used to using with SDCC didn't seem to be available.

For one, I couldn't find a way to get _ultoa or _utoa to actually work.  I did get _uitoa to work for up to 16-bit unsigned ints, but couldn't get the 32-bit or 8-bit optimized versions working.  And, none of the smaller sized printf functions seemed to be there either (i.e. printf_tiny, printf_small, printf_fast, etc).

It seems like you are the resident SDCC expert (are you one of the developers?)  Do you know if these are known issues where the library code just hasn't been ported yet, or am I doing something wrong?  Is there a list of supported library functions somewhere for these pdk devices?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 03, 2020, 05:26:54 am
For the "pdkuino.h" does it means that we can program pdk like an Arduino, or even make an Arduino core based on it?

Btw congratulation on reaching 1000th posts! You guys are doing some incredible jobs! :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 03, 2020, 05:40:40 am
spth,

I noticed when I was trying to optimize some of the code examples (specifically the adctest.c example) that certain functions that I am used to using with SDCC didn't seem to be available.

For one, I couldn't find a way to get _ultoa or _utoa to actually work.  I did get _uitoa to work for up to 16-bit unsigned ints, but couldn't get the 32-bit or 8-bit optimized versions working.  And, none of the smaller sized printf functions seemed to be there either (i.e. printf_tiny, printf_small, printf_fast, etc).

It seems like you are the resident SDCC expert (are you one of the developers?)  Do you know if these are known issues where the library code just hasn't been ported yet, or am I doing something wrong?  Is there a list of supported library functions somewhere for these pdk devices?

spth is the main developer of the PDK support in SDCC.

The printf from the standard includes results in code that is too big to fit into of the Padauk MCUs. I implemented some size optimized printf-like functions fore debugging here:

https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/PDK_softuart.c

This was with the aim of having a minimal memory overhead for debugging. One could probably implement a size optimized printf as well. But that needs to tie-in to standard libraries, that have not been set up yet. Your effort should be a good basis to finally tackle this as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 05:52:57 am
For the "pdkuino.h" does it means that we can program pdk like an Arduino, or even make an Arduino core based on it?

Well, we are pretty far away from that right now.

The biggest obstacle is that Arduino technically uses a C++ compiler, but SDCC is only a C compiler.  These PDK devices weren't even really designed with C in mind, let alone C++.  It is unlikely there will ever be a C++ compiler, or that it would be worth using if there was one.

Also, the limited RAM and program (CODE) size means we have to be much more frugal with how we write code and how libraries are written and used.  A 'simple' thing like printf (ok, not that simple in reality) can already consume more resources than a lot of these devices have.

But, we can make the environment feel a little more at home for those already versed in Arduino.  We can introduce helper macros and libraries that make interfacing with pins and peripherals and external devices look a bit more like Arduino code.  The pdkarduino.h include file in my repo really just introduces setup() and loop() methods so you don't have to manually create them (SDCC, like all C compilers just gives a main() method).  And I have a util.h file that helps us to write code a little more like with Arduino.

So, we can write things like:
Code: [Select]
#define PIN_LED PA,4
...
setPinOutput(PIN_LED);
setPinHigh(PIN_LED);

Instead of something like this:
Code: [Select]
PAC &= ~(1<<4)
PA |= (1<<4)

There are readability and portability improvements by using something like the first more Arduino like example (although I understand not everyone prefers that syntax).

There is also a possibility to integrate the toolchain into the Arduino IDE (although, IMO there are much better IDEs out there).  I ran across this the other day, which accomplishes an SDCC toolchain available to import into the Arduino IDE: https://github.com/DeqingSun/ch55xduino

There is still a lot of work to make the software libraries and example programs as clean and easy to use as Arduino provides, but hopefully we can at least start to bridge that gap.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 03, 2020, 06:01:08 am
Bit / reset instructions are working for I/O in SDCC 4.0.2 #11707 now.
Oh, that's interesting.   :-+  Does this mean that we can use __bit now (or even bitfields), or just that SDCC will choose to generate more set0/set1 instructions for more case?

It just means that SDCC will generate more set0 / set1.

Code: [Select]
__sfr __at(0x17) SFR;

void f(void)
{
    SFR |= 0x40; // Will use set1
    SFR &= 0x7f; // Will use set0
    SFR ^= 0x13; // Will use xor IO, a on pdk15
}

__bit would be for variables in data memory, but isn't implemented yet (__sbit would be the equivalent for I/O, not yet implemented either). Also bit-fields still only work for normal objects (as covered by the C standard), not for __sfr I/O i.e. an SDCC extension).

P.S.: Edited to fix formatting of code (had used the GitHub syntax before, while the syntax for code is different on this forum)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 06:02:07 am
spth is the main developer of the PDK support in SDCC.

Thanks. I was just reading through the SDCC changelog, and definitely saw his name all over the pdk stuff.

Quote
The printf from the standard includes results in code that is too big to fit into of the Padauk MCUs.

Well, technically it fits on the PFS173, but even still that is pretty wasteful of its resources.

Quote
I implemented some size optimized printf-like functions fore debugging here:

https://github.com/cpldcpu/SimPad/blob/master/Toolchain/library/PDK_softuart.c

This was with the aim of having a minimal memory overhead for debugging.

Yeah, I'll check that out more later.  But it would be nice to have something more accessible (i.e. included with SDCC) for 'standard' methods like 'printing' strings and numbers.

Quote
One could probably implement a size optimized printf as well. But that needs to tie-in to standard libraries, that have not been set up yet. Your effort should be a good basis to finally tackle this as well.

Yeah, that's what I was wondering about.  I have used the printf_small, and printf_tiny, etc... size optimized methods that SDCC has in the past.  I thought they were available for all devices, but it looks like they were only created for MCS51 (or maybe a few more, but definitely not all?).  I wonder how big of an undertaking that would be to create optimized versions for pdk?  We probably don't need to print floats all that often, but 8-32 bit signed/unsigned numbers would be helpful.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 06:03:46 am
It just means that SDCC will generate more set0 / set1.

~~~~
\_\_sfr \_\_at(0x17) SFR;

void f(void)
{
    SFR |= 0x40; // Will use set1
    SFR &= 0x7f; // Will use set0
    SFR ^= 0x13; // Will use xor IO, a on pdk15
}
~~~~

__bit would be for variables in data memory, but isn't implemented yet (__sbit would be the equivalent for I/O, not yet implemented either). Also bit-fields still only work for normal objects (as covered by the C standard), not for __sfr I/O i.e. an SDCC extension).

Ok thanks for clarifying.  That is still great progress.   :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 03, 2020, 06:06:52 am
For the "pdkuino.h" does it means that we can program pdk like an Arduino, or even make an Arduino core based on it?

Well, we are pretty far away from that right now.

The biggest obstacle is that Arduino technically uses a C++ compiler, but SDCC is only a C compiler.  These PDK devices weren't even really designed with C in mind, let alone C++.  It is unlikely there will ever be a C++ compiler, or that it would be worth using if there was one.

[…]

There is also a possibility to integrate the toolchain into the Arduino IDE (although, IMO there are much better IDEs out there).  I ran across this the other day, which accomplishes an SDCC toolchain available to import into the Arduino IDE: https://github.com/DeqingSun/ch55xduino (https://github.com/DeqingSun/ch55xduino)

There is still a lot of work to make the software libraries and example programs as clean and easy to use as Arduino provides, but hopefully we can at least start to bridge that gap.

You might also want to have a look at the sduino project, which created an arduion-like using STM8 with SDCC as compiler.

For those who really want C++ on Padauk: There is the LLVM+SDCC toolchain (http://www.colecovision.eu/llvm+sdcc/ (http://www.colecovision.eu/llvm+sdcc/)), but that is experimental stuff that needs more work, and I haven't worked on it since late 2016. AFAIR, back then, I got it to work good enough to put Dhrystone through it, and get it to work on STM8.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 03, 2020, 06:24:06 am
The biggest obstacle is that Arduino technically uses a C++ compiler, but SDCC is only a C compiler.  These PDK devices weren't even really designed with C in mind, let alone C++.  It is unlikely there will ever be a C++ compiler, or that it would be worth using if there was one.
For those who really want C++ on Padauk: There is the LLVM+SDCC toolchain (http://www.colecovision.eu/llvm+sdcc/ (http://www.colecovision.eu/llvm+sdcc/)), but that is experimental stuff that needs more work, and I haven't worked on it since late 2016. AFAIR, back then, I got it to work good enough to put Dhrystone through it, and get it to work on STM8.

Oh interesting.  But, I would imagine with the limited RAM and CODE sizes we are dealing with on these Padauk MCUs, that is asking for trouble, right?

There is also a possibility to integrate the toolchain into the Arduino IDE (although, IMO there are much better IDEs out there).  I ran across this the other day, which accomplishes an SDCC toolchain available to import into the Arduino IDE: https://github.com/DeqingSun/ch55xduino (https://github.com/DeqingSun/ch55xduino)
You might also want to have a look at the sduino project, which created an arduion-like using STM8 with SDCC as compiler.

Yeah, actually, the ch55xduino is a fork of the sduino project.  I briefly looked into sduino back in the day, but ended up going a different direction for the few projects I have done with STM8.  It was certainly an interesting concept.  I haven't looked at it recently.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 03, 2020, 06:46:58 am
The biggest obstacle is that Arduino technically uses a C++ compiler, but SDCC is only a C compiler.  These PDK devices weren't even really designed with C in mind, let alone C++.  It is unlikely there will ever be a C++ compiler, or that it would be worth using if there was one.
For those who really want C++ on Padauk: There is the LLVM+SDCC toolchain (http://www.colecovision.eu/llvm+sdcc/ (http://www.colecovision.eu/llvm+sdcc/)), but that is experimental stuff that needs more work, and I haven't worked on it since late 2016. AFAIR, back then, I got it to work good enough to put Dhrystone through it, and get it to work on STM8.

Oh interesting.  But, I would imagine with the limited RAM and CODE sizes we are dealing with on these Padauk MCUs, that is asking for trouble, right?

Not necessarily: SC22WG21, the standardization body for C++ wants to make C++ suitable for low-level devlopment. So carefully coded modern C++ should be similarly efficient as C, even on small devices. Of course, there are C++ features that have a high price in terms ofmemory, but you'd typically have to pay a similar price when coding an equivalent feature in C.
Also, the LLVM+SDCC combination gives you some of the high-level and interprocedural optimizations (where SDCC is lacking) together with SDCC optimizations aimed at small devices (which couldn't be easily implemented in GCC or LLVM). Back when I did the Dhrystone experiment, the Dhrystone that went through LLVM+SDCC was actually slightly faster than the one compiled with just SDCC. There was a substantial increase in code size, but only due to inefficient handling of static inline functions in SDCC. If that one feature was improved in SDCC, even the code size would have been lower with LLVM+SDCC than with plain SDCC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 03, 2020, 06:53:03 am
spth,

I noticed when I was trying to optimize some of the code examples (specifically the adctest.c example) that certain functions that I am used to using with SDCC didn't seem to be available.

For one, I couldn't find a way to get _ultoa or _utoa to actually work.  I did get _uitoa to work for up to 16-bit unsigned ints, but couldn't get the 32-bit or 8-bit optimized versions working.  And, none of the smaller sized printf functions seemed to be there either (i.e. printf_tiny, printf_small, printf_fast, etc).

It seems like you are the resident SDCC expert (are you one of the developers?)  Do you know if these are known issues where the library code just hasn't been ported yet, or am I doing something wrong?  Is there a list of supported library functions somewhere for these pdk devices?

All functions from the C standard that are in SDCC headers should just work.
_ultoa, etc are SDCC-specific extensions that just haven't been ported yet (the situation with these needs to first be improved anyway - they are not tested in regression tests, and they have bad names - as compiler-specific extensions hteir names should start with two underscores to not conflict with functions written by the user).

P.S.: I just opened a ticket for these functions: https://sourceforge.net/p/sdcc/bugs/3077/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on July 04, 2020, 06:42:22 pm
Hi everyone!

After finally having a programmer (thank you tim_!) I got started programming my PFS173 mikrocontrollers.
I quickly realized that I was badly missing an easy overview of the available pins and their functions (the overview in the datasheet is not that nice to look at).
Therefore I made a simple tool to generate pinout diagrams. For now, I added diagrams for all PFS173 packages.
The source code is at GitHub; adding diagrams for the other Padauk mikrocontrollers shouldn't be hard, if desired: https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226 (https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226)
The main issue right now is that the diagrams are super wide and look bad on smaller screens.
Let me know what you think!

https://christianflach.de/ic-pinout-diagram-generator (https://christianflach.de/ic-pinout-diagram-generator)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 05, 2020, 06:56:56 am
A few parts are pretty challenging for beginners, for example the calibration..., it took me almost a whole day to figure out how the hello world program works.  :phew:

This was the most diifficult hello world code I've ever seen :)
Code: [Select]
ihrcr = *((const unsigned char*)(0x87ed)); // took me hours to find where from the 0x8000 comes
https://github.com/free-pdk/sdcc-pdk-code-examples/blob/master/hello-s16/hello.c

Work is underway to try and standardize include files and example programs: (e.g. https://github.com/free-pdk/easy-pdk-programmer-software/pull/33)

This is still a work in progress, but I have committed a bunch of new (hopefully easier to understand) examples to the new "free-pdk-examples" repo (https://github.com/free-pdk/free-pdk-examples) that make use of the new "pdk-includes" (https://github.com/free-pdk/pdk-includes) and "easy-pdk-includes" (https://github.com/free-pdk/easy-pdk-includes) repos.

These example programs are loosely modeled after the examples included with Arduino.

Code Examples:

More examples and better README.md files are on their way over the next few days.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 05, 2020, 07:01:29 am
All functions from the C standard that are in SDCC headers should just work.
_ultoa, etc are SDCC-specific extensions that just haven't been ported yet (the situation with these needs to first be improved anyway - they are not tested in regression tests, and they have bad names - as compiler-specific extensions hteir names should start with two underscores to not conflict with functions written by the user).

P.S.: I just opened a ticket for these functions: https://sourceforge.net/p/sdcc/bugs/3077/

Thanks spth!

An additional question...

When looking at the generated .asm files, I am seeing code like:
Code: [Select]
mov a, p
mov p, a
idxm p, a
ceqsn a, p
etc...

But, I don't see any reference to a register named 'p' in the datasheets or .INC files.  Do you know if this is just a memory address that SDCC reserves for its own use, or an undocumented register, or something else?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 05, 2020, 07:05:55 am
I quickly realized that I was badly missing an easy overview of the available pins and their functions (the overview in the datasheet is not that nice to look at).
Therefore I made a simple tool to generate pinout diagrams. For now, I added diagrams for all PFS173 packages.
The source code is at GitHub; adding diagrams for the other Padauk mikrocontrollers shouldn't be hard, if desired: https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226 (https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226)
The main issue right now is that the diagrams are super wide and look bad on smaller screens.
Let me know what you think!

https://christianflach.de/ic-pinout-diagram-generator (https://christianflach.de/ic-pinout-diagram-generator)

I agree that they are a bit too wide, but otherwise those are very nice diagrams!

One thought... Since you are color-coding the blocks, you don't necessarily need to keep them in aligned columns.  That would reduce the width a bit.

It would be great to have these published to https://free-pdk.github.io/ (https://github.com/free-pdk/free-pdk.github.io).  If would be nice to have a page per IC with pinout diagrams and other useful information.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: greenpossum on July 05, 2020, 08:47:59 am
The source code is at GitHub; adding diagrams for the other Padauk mikrocontrollers shouldn't be hard, if desired: https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226 (https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/96578800d1e2ad50d6beccc5705d3ac240b117b6/src/App.js#L5-L226)

Hi cmfcmf,

Very nice. Is it possible to generalise it for other MCUs, maybe take the input data from a file, and an easier way to edit? A generator-generator?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 05, 2020, 11:19:16 am
All functions from the C standard that are in SDCC headers should just work.
_ultoa, etc are SDCC-specific extensions that just haven't been ported yet (the situation with these needs to first be improved anyway - they are not tested in regression tests, and they have bad names - as compiler-specific extensions hteir names should start with two underscores to not conflict with functions written by the user).

P.S.: I just opened a ticket for these functions: https://sourceforge.net/p/sdcc/bugs/3077/

Thanks spth!

An additional question...

When looking at the generated .asm files, I am seeing code like:
Code: [Select]
mov a, p
mov p, a
idxm p, a
ceqsn a, p
etc...

But, I don't see any reference to a register named 'p' in the datasheets or .INC files.  Do you know if this is just a memory address that SDCC reserves for its own use, or an undocumented register, or something else?

It's is 2 byte variable added by SDCC. Added probably to optimize code, i see it being used in loop counter. Also it is guaranteed to be aligned in memory and able to be addressed by instructions operating on 2 bytes, like ldt16 stt16. If you gonna use that instructions on another uint16_t it may or may not work, depends where linker would place variable in memory. Example:
Code: [Select]
//Assuming variables are place in presented order
uint16_t t16counter; // ldt16 will work
uint8_t somevar;
uint16_t sect16count; //ldt16 will fail, not aligned
uint8_t secsome;
uint16_t tht16count; //ldt16 will work

That is why in my i2c-fancontroller example I'm using ldt16 on p, then moving p to acc and then from acc to 'final' variable. Very inefficient but i can't guarantee placement of 'final' variable.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on July 05, 2020, 02:17:55 pm

One thought... Since you are color-coding the blocks, you don't necessarily need to keep them in aligned columns.  That would reduce the width a bit.

It would be great to have these published to https://free-pdk.github.io/ (https://github.com/free-pdk/free-pdk.github.io).  If would be nice to have a page per IC with pinout diagrams and other useful information.

I have added an option to adjust the font size and toggle between "aligned" and "dense" mode as well as download buttons.
I agree that the diagrams should be on https://free-pdk.github.io/. I think it would make a lot of sense to use GitHub's Jekyll integration to generate the documentation pages from Markdown instead of writing plain HTML.
I'll see if I can get something nice to work.

Hi cmfcmf,

Very nice. Is it possible to generalise it for other MCUs, maybe take the input data from a file, and an easier way to edit? A generator-generator?

Yes! I have cleaned the project up a bit and all chip data is now located in this file: https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/master/src/chips.js (https://github.com/cmfcmf/ic-pinout-diagram-generator/blob/master/src/chips.js). Other chips can be added in there. To preview changes locally, follow the instructions in the README file.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 05, 2020, 03:16:23 pm

One thought... Since you are color-coding the blocks, you don't necessarily need to keep them in aligned columns.  That would reduce the width a bit.

It would be great to have these published to https://free-pdk.github.io/ (https://github.com/free-pdk/free-pdk.github.io).  If would be nice to have a page per IC with pinout diagrams and other useful information.

I have added an option to adjust the font size and toggle between "aligned" and "dense" mode as well as download buttons.
I agree that the diagrams should be on https://free-pdk.github.io/. I think it would make a lot of sense to use GitHub's Jekyll integration to generate the documentation pages from Markdown instead of writing plain HTML.
I'll see if I can get something nice to work.

Jekyll would be great. We could then also use that space for instruction/tutorials.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 05, 2020, 06:09:30 pm
When looking at the generated .asm files, I am seeing code like:
Code: [Select]
mov a, p
mov p, a
idxm p, a
ceqsn a, p
etc...

But, I don't see any reference to a register named 'p' in the datasheets or .INC files.  Do you know if this is just a memory address that SDCC reserves for its own use, or an undocumented register, or something else?

p is a "pseudo-register", i.e. a memory location handled by the compiler as if it was a register. It is physically located at address 0 (which means we know it is aligned, and in the lower half of the address space, so all instructions work on this location).

P.S.: In retrospective, I think more pseudo-registers should be used. But this is a trade-off: More pseudo-registers allow SDCC to generate better code, but they also need to be saved at interrupts, increasing interrupt latency. Still, I now think the sweet spot is at 3 consecutive bytes of pseudo.registers, starting at address 0 (that way, one could have p0, p1, p2. p0 together with p1 would be used for access to the 16-bit timer and for ldtabl. Having both p0 and p2 would allow more efficient copies between two stack locations). But changing the number of pseudo-registers is a long-term thing, and also needs to be coordinated with future pdk16 support.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 05, 2020, 07:23:59 pm
p is a "pseudo-register", i.e. a memory location handled by the compiler as if it was a register. It is physically located at address 0 (which means we know it is aligned, and in the lower half of the address space, so all instructions work on this location).

P.S.: In retrospective, I think more pseudo-registers should be used. But this is a trade-off: More pseudo-registers allow SDCC to generate better code, but they also need to be saved at interrupts, increasing interrupt latency. Still, I now think the sweet spot is at 3 consecutive bytes of pseudo.registers, starting at address 0 (that way, one could have p0, p1, p2. p0 together with p1 would be used for access to the 16-bit timer and for ldtabl. Having both p0 and p2 would allow more efficient copies between two stack locations). But changing the number of pseudo-registers is a long-term thing, and also needs to be coordinated with future pdk16 support.

Thanks for the explanation!

Is it safe to assume that 'p' can be modified in an inline assembly method without worrying about saving/restoring?  i.e. does the caller already save/restore 'p' if it uses it, or should the callee do the save/restore?

I agree that having another pseudo-register or two would be helpful for juggling things around. +1 for eventually getting that implemented.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 05, 2020, 08:56:07 pm
Is it safe to assume that 'p' can be modified in an inline assembly method without worrying about saving/restoring?  i.e. does the caller already save/restore 'p' if it uses it, or should the callee do the save/restore?

Both a and p are saved by the caller, if necessary.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on July 05, 2020, 09:05:36 pm

One thought... Since you are color-coding the blocks, you don't necessarily need to keep them in aligned columns.  That would reduce the width a bit.

It would be great to have these published to https://free-pdk.github.io/ (https://github.com/free-pdk/free-pdk.github.io).  If would be nice to have a page per IC with pinout diagrams and other useful information.

I have added an option to adjust the font size and toggle between "aligned" and "dense" mode as well as download buttons.
I agree that the diagrams should be on https://free-pdk.github.io/. I think it would make a lot of sense to use GitHub's Jekyll integration to generate the documentation pages from Markdown instead of writing plain HTML.
I'll see if I can get something nice to work.

Jekyll would be great. We could then also use that space for instruction/tutorials.

I have created a PR [1] that introduces a new design for https://free-pdk.github.io/ and also integrates the pinout diagrams as well as an overview of the many different free-pdk repositories. There is a lot of room for further improvements, but this should get the ball rolling when it comes to tutorials and more detailed instructions. Adding pages is as easy as adding new markdown files (no more HTML :)).
I have not yet added any information on the SDCC examples and headers, since that is an ongoing discussion.

[1] https://github.com/free-pdk/free-pdk.github.io/pull/3
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 06, 2020, 12:00:11 am

One thought... Since you are color-coding the blocks, you don't necessarily need to keep them in aligned columns.  That would reduce the width a bit.

It would be great to have these published to https://free-pdk.github.io/ (https://github.com/free-pdk/free-pdk.github.io).  If would be nice to have a page per IC with pinout diagrams and other useful information.

I have added an option to adjust the font size and toggle between "aligned" and "dense" mode as well as download buttons.
I agree that the diagrams should be on https://free-pdk.github.io/. I think it would make a lot of sense to use GitHub's Jekyll integration to generate the documentation pages from Markdown instead of writing plain HTML.
I'll see if I can get something nice to work.

Jekyll would be great. We could then also use that space for instruction/tutorials.

I have created a PR [1] that introduces a new design for https://free-pdk.github.io/ and also integrates the pinout diagrams as well as an overview of the many different free-pdk repositories. There is a lot of room for further improvements, but this should get the ball rolling when it comes to tutorials and more detailed instructions. Adding pages is as easy as adding new markdown files (no more HTML :)).
I have not yet added any information on the SDCC examples and headers, since that is an ongoing discussion.

[1] https://github.com/free-pdk/free-pdk.github.io/pull/3

Your pr is way superior than my pr! In honest it looks really awesome! I am gonna close my pr after they merged your pr.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 06, 2020, 05:10:12 pm

I have created a PR [1] that introduces a new design for https://free-pdk.github.io/ and also integrates the pinout diagrams as well as an overview of the many different free-pdk repositories. There is a lot of room for further improvements, but this should get the ball rolling when it comes to tutorials and more detailed instructions. Adding pages is as easy as adding new markdown files (no more HTML :)).
I have not yet added any information on the SDCC examples and headers, since that is an ongoing discussion.

[1] https://github.com/free-pdk/free-pdk.github.io/pull/3

https://free-pdk.github.io/

It's live now, thanks a lot!

Now it's much easier to contribute some much needed documentation. Everyone, feel free to contribute. You can directly submit pull-requests here: https://github.com/free-pdk/free-pdk.github.io/tree/development

I will add a section about ordering the lite-programmer once I received and validated the r1 samples - they are being made right now.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 06, 2020, 05:20:37 pm

I have created a PR [1] that introduces a new design for https://free-pdk.github.io/ and also integrates the pinout diagrams as well as an overview of the many different free-pdk repositories. There is a lot of room for further improvements, but this should get the ball rolling when it comes to tutorials and more detailed instructions. Adding pages is as easy as adding new markdown files (no more HTML :)).
I have not yet added any information on the SDCC examples and headers, since that is an ongoing discussion.

[1] https://github.com/free-pdk/free-pdk.github.io/pull/3

https://free-pdk.github.io/

It's live now, thanks a lot!

Now it's much easier to contribute some much needed documentation. Everyone, feel free to contribute. You can directly submit pull-requests here: https://github.com/free-pdk/free-pdk.github.io/tree/development

I will add a section about ordering the lite-programmer once I received and validated the r1 samples - they are being made right now.

Excellent!  Nice work!

A few things I noticed while playing around with the pinout diagrams:

I also just submitted PRs for:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 06, 2020, 08:51:47 pm
Just as a side note: How can the PMS150C be so cheap?

The image below shows a die size comparison between a PIC12C508 (sorry, wrong title) and a PMS150C. I don't know the actual dimension of the PIC die - the image is from Zeptobars.
One can, however, use the size of the bondbands to scale the images relative to each other. The PMS150C is around 10x smaller than the PIC, thanks to newer technology.

Edit: Source of the images

- PIC: https://zeptobars.com/en/read/PIC12C508-PIC-Microchip
- Padauk: https://electronupdate.blogspot.com/2019/09/3-cent-microprocessor-teardow-paduak.html

[attachimg=1]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 06, 2020, 09:32:13 pm
From the 'new' website:


SDCC Integration

Padauk themselves use a custom programming language that looks a bit like C for programming the µCs that is compiled by their proprietary IDE. While code created using this custom language can be programmed using the Easy PDK Programmer, we still recommend using SDCC, especially if you want support for proper C code. Should you be interested in code samples in that custom language, look at free-pdk/simple-pdk-code-examples.


That highlighted part is actually incorrect.

Here is a PR to fix that: https://github.com/free-pdk/free-pdk.github.io/pull/8

I also submitted a PR to add ROM and RAM sizes: https://github.com/free-pdk/free-pdk.github.io/pull/6
We might want to turn that section into a table and have columns for the major peripherals (i.e. Instruction Set, ROM Size/Type, RAM Size, ADC, PWM, etc...)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on July 06, 2020, 10:38:49 pm

I have created a PR [1] that introduces a new design for https://free-pdk.github.io/ and also integrates the pinout diagrams as well as an overview of the many different free-pdk repositories. There is a lot of room for further improvements, but this should get the ball rolling when it comes to tutorials and more detailed instructions. Adding pages is as easy as adding new markdown files (no more HTML :)).
I have not yet added any information on the SDCC examples and headers, since that is an ongoing discussion.

[1] https://github.com/free-pdk/free-pdk.github.io/pull/3

https://free-pdk.github.io/

It's live now, thanks a lot!

Now it's much easier to contribute some much needed documentation. Everyone, feel free to contribute. You can directly submit pull-requests here: https://github.com/free-pdk/free-pdk.github.io/tree/development

I will add a section about ordering the lite-programmer once I received and validated the r1 samples - they are being made right now.

Excellent!  Nice work!

A few things I noticed while playing around with the pinout diagrams:
  • It would be nice if the diagrams were centered on the page.
  • Maybe provide a quick way to check/uncheck all.
  • For the 'Programming Pins', instead of RESET, maybe use ICVPP like it is labeled on the programmer schematic.  And maybe add an associated ICVDD on the VDD pin to help clarify that it is directly manipulated during programming.
    • PR submitted: https://github.com/cmfcmf/ic-pinout-diagram-generator/pull/3
  • I can help explain the datasheet for current sink/drive if needed.  What actual questions do you have?
    • PR submitted: https://github.com/cmfcmf/ic-pinout-diagram-generator/pull/4

I also just submitted PRs for:
  • Slightly better consistency with descriptions - https://github.com/cmfcmf/ic-pinout-diagram-generator/pull/5
  • Add support for PMS152 - https://github.com/cmfcmf/ic-pinout-diagram-generator/pull/6
  • Add support for PMS150C/PMS15A - https://github.com/cmfcmf/ic-pinout-diagram-generator/pull/7

Nice work with the PRs.

My confusion with the drive/sink currents in the PFS154 datasheet arose from the fact that it listed the drive/sink currents differently than the PFS173 datasheet:

PFS154PFS173
"negative drive current", e.g. -5mA"positive drive current, e.g. 5mA
"low" vs. "normal" current"normal" vs. "strong" current

But, looking at your PR, I gathered that both seem to mean the same thing.

Centering the diagrams is on my TODO list, however it currently breaks the image download buttons.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 06, 2020, 10:44:52 pm
My confusion with the drive/sink currents in the PFS154 datasheet arose from the fact that it listed the drive/sink currents differently than the PFS173 datasheet:

PFS154PFS173
"negative drive current", e.g. -5mA"positive drive current, e.g. 5mA
"low" vs. "normal" current"normal" vs. "strong" current

But, looking at your PR, I gathered that both seem to mean the same thing.

Yeah, I'm not sure why they state drive current as '-' in some datasheets but not others.

The low/normal vs. normal/strong has to do with the FUSE settings.  Some have an option to enable weaker IO drive, some have an option to enable stronger IO drive.

Quote
Centering the diagrams is on my TODO list, however it currently breaks the image download buttons.

 :-+  I took a quick look, but noticed these diagrams use html tables with varying width columns, so I gave up pretty quick.  Hopefully there is a clean way to do it.

EDIT:  Maybe the table can span diagrams instead of creating a new table per diagram?  Then, the column widths would line up between diagrams, and the entire table could be centered.  Not sure what that does to the image download though.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 07, 2020, 08:28:58 am
Sharing this here, in case anyone else would find it useful:

I threw together a quick-n-dirty node.js app that can 'rip' the Padauk IDE's .INC files into a more consumable .json form:
And, I used it to 'rip' the PDK .INC files for a bunch of the common devices that we are working with (all the .json files in the root of the repo).

https://github.com/serisman/pdk-device-json

Among other things, this should come in handy for auto-generating the pdk-include files, whenever we decide on the final format.

It also could come in handy to auto-generate documentation, or comparison tables, or just to manually compare two different devices through a compare tool, or whatever.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 07, 2020, 02:37:54 pm
In this description there is a mistake at STT16 M | LDT16 M | IDXM M,A | IDXM A,M instructions:
https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html (https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html)

000011c<7-bit MEM addr>c  // 7+7+1=15 bit, but this is only 14 bit device
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 08, 2020, 12:11:44 am
When will the Mini-pill programmer's kicad file available? It'll be fun to build one because it's such an impressive design!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 08, 2020, 12:19:46 am
When will the Mini-pill programmer available? It'll be fun to build one because it's such an impressive design!

Thanks for showing interest!  Indeed, it is a kinda fun build to do!  Probably not a good project from someone that hasn't already done some surface mount soldering before, though.  The STM32 in particular can be a bit more challenging than other parts.

The STM32 mini-pill board is already 'available':

I still have to post the design files for the Padauk programmer top-hat, but the PCBs are already available from OSHPARK (https://oshpark.com/shared_projects/z5EAm6HO (https://oshpark.com/shared_projects/z5EAm6HO)).  Or you can find the gerber files from my very first post (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3091725/#msg3091725 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3091725/#msg3091725)).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 08, 2020, 12:38:54 am
Since all of these padauk micros are surface mounted, I learned quite a lot of surface mounting soldering during the last two months. :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 08, 2020, 01:54:31 am
Since all of these padauk micros are surface mounted, I learned quite a lot of surface mounting soldering during the last two months. :-+

Excellent!  :-+

Although an LQFP-48 is quite a bit more difficult than a SOP-16.  But, definitely give it a try.  With a decent soldering iron, and some patience, it is fairly manageable.  Some good flux, de-soldering braid, and a magnifying lens will come in handy as well.

Just don't do what I did on the first one.  After carefully tacking down the first corner and repositioning the board so I could tack down the second corner, my OCD got the better of me and without thinking about it, I put my finger on the STM32 to 'clean' off the flux residue.  Let's just say, the pins were never straight again.  |O  I still might be able to fix it, but it was easier/quicker to just grab a spare pcb/ic and try again, this time even more carefullly.

So, maybe a good idea to make sure you have a spare STM32 as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 08, 2020, 03:15:44 am
Just don't do what I did on the first one.  After carefully tacking down the first corner and repositioning the board so I could tack down the second corner, my OCD got the better of me and without thinking about it, I put my finger on the STM32 to 'clean' off the flux residue.  Let's just say, the pins were never straight again.  |O  I still might be able to fix it, but it was easier/quicker to just grab a spare pcb/ic and try again, this time even more carefullly.

Ok, boo-boo all fixed.  I was able to pull off the IC with hot air, VERY carefully straighten out the bent pins, and tack it back on with hot air again.  I went around and flooded all the pins with solder, and used wick to pull the excess back off.  Some of the pins are still a little out of shape, but as far as I can tell they are all making contact and no shorts (I did clean up the joints a bit further after taking the 'After' picture).  I finished assembly of the rest of the board and can at least confirm that the USB bootloader works.

Before:
[Attach=1]

After:
[Attach=2]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 08, 2020, 03:31:07 pm
Hi,

I created a new showcase repository which will receive complete and useful projects:

https://github.com/free-pdk/easy-pdk-showcase-projects

I spent some time to also create pc emulation code which uses the same (main) source code for emulation. This should make modifications / implementing new features much easier.

All projects are fully self contained and do not have any external dependencies. You only need to install the latest SDCC compiler and you are ready to go.

Projects so far:

* WS2812b RGB LED 16x16 matrix animation demo (inspired from here: https://github.com/joshgerdes/arduino-led-matrix):

https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/ws2812animation16x16

- universal WS2812B output routine (adopted from cpldcpu's implementation)
- on the fly RLE image decoder
- image packer which compresses the 16x16 RGB images to palette based RLE encoded images (compression factor 15:1)
  The original project for Arduino nano produced apx. 40kB of code. The compressed image version for PADAUK MCUs requires less than 2.5kB.
- the complete project fits into 3K ICs like the PFS173. Reduced versions for 2K and 1K ICs are created automatically (some images/animations left out).
- targets for PMS150C, PFS154, PFS172, PFS173
- emulation project for pc (Linux/MacOS/Windows) - have a look in the emulation directory


* Polyphonic sound player emulating the 4 NES sound and playing a famous tune (ported from: https://bisqwit.iki.fi/jutut/kuvat/programming_examples/pic/):

https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/polysound

- stand alone 4 channel NES style music player (requires no extra hardware other than a speaker)
- requires 3K IC like PFS173
- emulation project for pc (Linux/MacOS/Windows) - have a look in the emulation directory

More to come soon  8)

WS2812 16x16 matrix demo:
[attachimg=1]

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 08, 2020, 03:45:34 pm
In this description there is a mistake at STT16 M | LDT16 M | IDXM M,A | IDXM A,M instructions:
https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html (https://free-pdk.github.io/PADAUK_FPPA_14_bit_instruction_set.html)

000011c<7-bit MEM addr>c  // 7+7+1=15 bit, but this is only 14 bit device

This is a bit tricky to explain...

The "7 bit memory address" label is correct, just the last bit is ignored and reused as "c".

This means the address is 7 bit with the last bit set to 0 (You only can address every second byte).

I tried to explain this in the comment for the instructions: "(last bit of M set to 0, M must be word aligned)"

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 09, 2020, 06:48:50 am
Thanks for sharing JS 8) :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 09, 2020, 07:33:38 am
Thanks for sharing JS 8) :-+

Yes, agreed!

That polysound example is simply amazing.

I may have to pick up one of those 16x16 WS2812B matrix displays as well, cause that other project looks like fun too.

Both of these projects make me wonder how easy it would be to combine them with an inexpensive NOR flash IC (i.e. W25Q80 or similar) to greatly increase the quantity/duration of the sounds/patterns and allow them to be changed even without having to re-compile.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 09, 2020, 07:40:53 am
FYI,

I cleaned up some of the code and comments in the (in-progress) free-pdk-examples repo (https://github.com/free-pdk/free-pdk-examples) and added README files to the first three examples.

The repo is now also more self-sufficient (it has copies of all the required include files instead of using git submodules).

More to come over the next few days.

I still need to give the repo a proper license, make sure all 'original authors' are properly referenced, clean up the serial code a bit, add more README files, and write the rest of the intended examples.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 09, 2020, 08:30:01 am
Both of these projects make me wonder how easy it would be to combine them with an inexpensive NOR flash IC (i.e. W25Q80 or similar) to greatly increase the quantity/duration of the sounds/patterns and allow them to be changed even without having to re-compile.

I already completed a project with external SPI flash - a good quality audio player (plays 8 bit @32kHz).
I created a PCB which holds an 8 pin PADAUK (e.g. PMS150C/PFS154/PFS173) and added a 16MBit SPI flash and a small class D amplifier.
I use it inside of my hackintosh to play the startup chime immediately after a power cycle.  8)

In order to release this project I still need to write the pc emulation part (not so hard now since I got perfect audio emulation working in polysound already).

I also added a microSD card socket to the PCB mentioned above and want to try to use this as external storage (most likely without file system since we simply don't have enough memory).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 09, 2020, 09:30:09 am
Thanks to @cmfcmf we now have a list of community projects on https://free-pdk.github.io/ (scroll to bottom). (Thanks again!)

[attach=1]

The list is automatically populated by a Github search. To be included, please do the following:

 - Add "padauk" as a topic for your repository
 - Add a project description

[attachimg=2]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 09, 2020, 11:57:14 am
Quote
already completed a project with external SPI flash - a good quality audio player (plays 8 bit @32kHz).
I created a PCB which holds an 8 pin PADAUK (e.g. PMS150C/PFS154/PFS173) and added a 16MBit SPI flash and a small class D amplifier.
I use it inside of my hackintosh to play the startup chime immediately after a power cycle.  8)
A video Demo of some sort would be very nice 8) ;)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 09, 2020, 01:43:38 pm
Thanks.

Another confusing instructions are T0SN M.n | T1SN M.n | SET0 M.n | SET1 M.n. The table shows 6-bit MEM addr, but for M address you need 7 bit address to be able to address the whole memory. (128bytes PFS154) For IO space needs 6 bit because it is only 64bytes.

I wrote a pure assembler, finished now, testing is in progress. That's why I need to know how every instruction works.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 09, 2020, 01:58:33 pm
Thanks.

Another confusing instructions are T0SN M.n | T1SN M.n | SET0 M.n | SET1 M.n. The table shows 6-bit MEM addr, but for M address you need 7 bit address to be able to address the whole memory. (128bytes PFS154) For IO space needs 6 bit because it is only 64bytes.

I wrote a pure assembler, finished now, testing is in progress. That's why I need to know how every instruction works.

This is also correct and is indeed a limitation of the processor. Those instructions only can address the lower address space. It's also mentioned in the data sheets.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 09, 2020, 02:22:47 pm
The audio player showcase project is available now: https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/audioplayer


A video Demo of some sort would be very nice 8) ;)
What kind of video demo? A video from my hackintosh (intel NUC) starting up?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 09, 2020, 03:36:26 pm
I experiance so many strange things around this MCU :D

I run my PFS154 on ILRC but according to my calculation it runs approx. at 143kHz. I wrote a loop with 97nop + 1 goto + 1 xor (to invert led), that's 100 instruction, the execution of the 100 instruction takes 700us, so to execute 1 instruction takes 7us. I don't find any explanation for this. According to the datasheet it should run at 55kHz. I know ILRC is not accurate but I did not expect 143kHz.

Code: [Select]
.rom
wdreset
set0  clkmd.1
set1 pac.0
mov a,#01h
label1:
xor   pa,a
nop
nop
        ...
        97 nops total
        goto label1
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 09, 2020, 04:58:32 pm
I experiance so many strange things around this MCU :D

I run my PFS154 on ILRC but according to my calculation it runs approx. at 143kHz. I wrote a loop with 97nop + 1 goto + 1 xor (to invert led), that's 100 instruction, the execution of the 100 instruction takes 700us, so to execute 1 instruction takes 7us. I don't find any explanation for this. According to the datasheet it should run at 55kHz. I know ILRC is not accurate but I did not expect 143kHz.

Did you properly setup ILRC using the factory calibration value?

Philipp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 10, 2020, 11:27:49 am
I wrote a very simple code again, after reset I put the clkmd register value to port B.

Code: [Select]
.rom
wdreset
mov a,#ffh
mov pbc,a
mov a,clkmd
mov pb,a
label1:
wdreset
nop
nop
nop
        goto label1

According to PFS154 datasheet clkmd value after reset should be: 0xF6
I read 0x9E

This means clock select type is 1, and clock mode is IHRC/64 = so 16MHz / 64 = 250kHz
If one instruction is executed in 2 cycles, and I did not calibrated the IHRC, that could answer the question why my PFS154 running at 143kHz

It's very annoying if we can not trust in the data sheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 10, 2020, 11:49:18 am
I wrote a very simple code again, after reset I put the clkmd register value to port B.

Code: [Select]
.rom
wdreset
mov a,#ffh
mov pbc,a
mov a,clkmd
mov pb,a
label1:
wdreset
nop
nop
nop
        goto label1

According to PFS154 datasheet clkmd value after reset should be: 0xF6
I read 0x9E

This means clock select type is 1, and clock mode is IHRC/64 = so 16MHz / 64 = 250kHz
If one instruction is executed in 2 cycles, and I did not calibrated the IHRC, that could answer the question why my PFS154 running at 143kHz

It's very annoying if we can not trust in the data sheet.

The data sheet is also right... Usually PADAUK initializes the default values inside of the startup code they insert when you use the PADAUK IDE.
Since you use your own assembler / compiler you have to re-create the startup code and initializations.
BTW: PADAUK startup code wastes up to 10% of the valuable code memory.

Anyway, a good practice is to always set the complete value yourself.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 10, 2020, 12:14:47 pm
Yeah, but this is very misleading even if Padauk IDE users won't experience this problem.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 10, 2020, 01:11:55 pm
They expect that you use their IDE only, at least for now. Also in datasheet there is no information about some registers, like MISC_LVR, ROP, they are indirectly mentioned in "Code Options" chapter but without any address or 'how to'. I just wonder why ? Because this options shouldn't be changed after initialization ?, or maybe because this options differ to much between uC and they want maximum code compatibility.

Also anyone know how PADAUK see that whole open-source toolchain ? They gonna try support/kill it or maybe do nothing about it ?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 10, 2020, 05:14:05 pm
Also anyone know how PADAUK see that whole open-source toolchain ? They gonna try support/kill it or maybe do nothing about it ?

I don't think they'll kill this project. Larger companies that uses padauk product have to use their own "toolchain" because that's the only toolchain with official support.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 11, 2020, 07:28:47 am
Quote
What kind of video demo? A video from my hackintosh (intel NUC) starting up?
That would be nice, also other cool projects that you do, like the polysound demo >:D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on July 11, 2020, 09:22:59 am
Also anyone know how PADAUK see that whole open-source toolchain ? They gonna try support/kill it or maybe do nothing about it ?

I don't know if they have any plans for it.
But they have been helping so far (answering techical questions, even on undocumented features, providing some free samples of devices that were at the time not yet available via the normal supply chains).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 11, 2020, 11:23:14 am
Just made one of Tim's lite programmers.
My first STM32 SMD soldering job, have only tried AVR SMD before  :phew:

Tim sent me two , and i totally screwed up the first one ... Tacked down 2 sides but began drag soldering on the tacked side  |O
MCU badly misaligned , and when trying to correct i badly bent 4 pins.

Well the 2'nd went ok i think , i can DFU program it w. the programer sw.

Now off to solder a PADA to a SMD-DIP board.

Edit: It's alive
Code: [Select]
./easypdkprog -v probe
Searching programmer... found: /dev/ttyACM3
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.2 Protocol:1.2
Probing IC... found.
TYPE:FLASH RSP:0xAA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 11, 2020, 12:46:14 pm
I played with LVR settings yesterday, it works pretty well.

I know I have to load these values to misclvr register (0x1B)
0x00 - 4V
0x20 - 3.5V
0x40 - 3V
0x60 - 2.75V
0x80 - 2.5V
0xA0 - 1.8V
0xC0 - 2.2V
0xE0 - 2V

But I did not find info how security (MTP code protection), boot-up time, drive (IO low/normal driving) works, so the rest of Code Options chapter is unclear for me.
misc.5 controls the wake-up time but I am not sure it is the same thing what mentioned in Code Options chapter.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 11, 2020, 01:54:09 pm
But I did not find info how security (MTP code protection), boot-up time, drive (IO low/normal driving) works, so the rest of Code Options chapter is unclear for me.
misc.5 controls the wake-up time but I am not sure it is the same thing what mentioned in Code Options chapter.

This might help you: https://github.com/free-pdk/easy-pdk-programmer-software/pull/30#issuecomment-650870921

Just made one of Tim's lite programmers.
My first STM32 SMD soldering job, have only tried AVR SMD before  :phew:

Tim sent me two , and i totally screwed up the first one ... Tacked down 2 sides but began drag soldering on the tacked side  |O
MCU badly misaligned , and when trying to correct i badly bent 4 pins.

Well the 2'nd went ok i think , i can DFU program it w. the programer sw.

Now off to solder a PADA to a SMD-DIP board.

Buy yourself good flux (paste/gel), it's unbelievable  what difference it can make, it's magic. I build 2 original programmers and i was struggling with first one, for 2nd i used better flux and it was smooth, soldered tqfp48 without using copper wick , joints nicely shine. Now i have programmer for stable and dev easy-pdk branch.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 11, 2020, 05:22:52 pm

Just made one of Tim's lite programmers.
My first STM32 SMD soldering job, have only tried AVR SMD before  :phew:

Tim sent me two , and i totally screwed up the first one ... Tacked down 2 sides but began drag soldering on the tacked side  |O
MCU badly misaligned , and when trying to correct i badly bent 4 pins.

Well the 2'nd went ok i think , i can DFU program it w. the programer sw.

Now off to solder a PADA to a SMD-DIP board.

Buy yourself good flux (paste/gel), it's unbelievable  what difference it can make, it's magic. I build 2 original programmers and i was struggling with first one, for 2nd i used better flux and it was smooth, soldered tqfp48 without using copper wick , joints nicely shine. Now i have programmer for stable and dev easy-pdk branch.

I did use good flux , and a Metcal Hoof.

But when you are foolish enough to dragsolder first "drag" on one of the sides tacked down , the package will move.
I did not make that mistake on the 2'nd board.

I might find my hot-air and remove the MCU. I doubt i'll spend time trying to save those bent pins. But i might get another MCU, when i have an order at LCSC.

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 11, 2020, 08:50:07 pm
But I did not find info how security (MTP code protection), boot-up time, drive (IO low/normal driving) works, so the rest of Code Options chapter is unclear for me.
misc.5 controls the wake-up time but I am not sure it is the same thing what mentioned in Code Options chapter.

Some of those bits are encoded in "fuse bits" in last word of memory.

Here is example from PFS173 like I defined in PFS173.h in examples folder in programmer software:
#define FUSE_SECURITY_OFF  0x0001 //(S)
#define FUSE_SECURITY_ON   0x0000
#define FUSE_PB4PB5_NORMAL 0x0000 //(D)
#define FUSE_PB4PB5_STRONG 0x0100
#define FUSE_BOOTUP_SLOW   0x0000 //(B)
#define FUSE_BOOTUP_FAST   0x1800
#define FUSE_RES_BITS_HIGH 0x62FC // - 1 1 B   B 0 1 D   1 1 1 1   1 1 0 S => 0x62FC

All this can be learned from PFS173.INC from PADAUK IDE "INC_PDK" folder.


After you managed the fuses you also will need to find out how to tune the internal oscillator. Otherwise you will experience something like 6.5 MHz instead of 8MHz SYSCLOCK...

EASY PDK programmer defines placeholder macros (in assembly) for tuning which will be dynamically inserted and altered during programing.

Have a look at development branch for the macro definition: https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/easypdk/pdkcommon.h 
and at https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/easypdk/pfs173.h to see how they are used.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 07:28:36 am
I just tried the two blinky's from here wo. IRQ & w. irq
https://github.com/free-pdk/free-pdk-examples

Edit: MCU type - PFS154-S16

My led blinks at a rate of approx 2 sec , it should be approx 1 sec.

I run @4.0v
Code: [Select]
Assumption (DS) IHRC  = 16MHz
SysClock = IHRC/16

Timer16 irq (bit8) - every  512 cycles

ticks every 16000000/512 = 31250 clock cycles    should be ~32uS


I'm toggling PB3 in the timer ISR , just to be able to put a scope on
Scope - PB3 toggle


Tick IHRC = 58,4uS
Tick sysclock = 888uS



Seems like Sysclock is set correct
Code: [Select]
                                    483 ; main.c: 64: AUTO_INIT_SYSCLOCK();
                                    484 ; genAssign
      00010A 1C 2F                  485 mov a, #0x1c
      00010C 83 01                  486 mov __clkmd, a

So is t16

Code: [Select]
      000000                        232 _millis_setup:
                                    233 ; ../include/millis.h: 29: T16M = (uint8_t)(T16M_CLK_IHRC | T16M_CLK_DIV1 | T16M_INTSRC_8BIT);
                                    234 ; genAssign
      000000 80 2F                  235 mov a, #0x80
      000002 86 01                  236 mov __t16m, a

I'm new @this MCU , and if i didn't know better , i'd say the MCU runs 8MHz or the divider is ???


Any tips

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 08:24:15 am
Hmm

Replacing
AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);

with

PDK_USE_FACTORY_IHRCR_16MHZ();           //use factory calibration value


Makes the tick's (timer irq)  34.40 uS wide

That's a lot closer to the 31.25 (Calculated value)

Is the AutoCalibrate always that "full" of surprises , and what if this wasn't a 154 or 173 (that has Factory IHCR value)

Using
//EASY_PDK_USE_FACTORY_IHRCR_16MHZ();           //use factory calibration value
Gives a compile error ... unknown



/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 08:53:22 am
What does this

487 ;   main.c: 70: AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);
And forward do ??

It does a lot of magic w. accumulator a , but never saves it anywhere  - It just does that stuff , and then returns 0x00 in a.


Code: [Select]
                                    478 ; -----------------------------------------
                                    479 ; function _sdcc_external_startup
                                    480 ; -----------------------------------------
                                    481 ; Register assignment is optimal.
      00010A                        482 __sdcc_external_startup:
                                    483 ; main.c: 65: AUTO_INIT_SYSCLOCK();
                                    484 ; genAssign
      00010A 1C 2F                  485 mov a, #0x1c
      00010C 83 01                  486 mov __clkmd, a
                                    487 ; main.c: 70: AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);
                                    488 ; genInline
      00010E 52 2C                  489 and a, #'R'                       
      000110 43 2C                  490 and a, #'C'                       
      000112 01 2C                  491 and a, #(1)           
      000114 40 2C                  492 and a, #((1000000))     
      000116 42 2C                  493 and a, #((1000000)>>8) 
      000118 0F 2C                  494 and a, #((1000000)>>16)
      00011A 00 2C                  495 and a, #((1000000)>>24)
      00011C A0 2C                  496 and a, #((4000))     
      00011E 0F 2C                  497 and a, #((4000)>>8) 
      000120 0B 2C                  498 and a, #(0x0b)             
                                    499 ; main.c: 82: return 0;   // Return 0 to inform SDCC to continue with normal initialization.
                                    500 ; genReturn
                                    501 ; genLabel
                                    502 ; peephole j0 removed unused label 00101$.
                                    503 ; main.c: 83: }
                                    504 ; genEndFunction
      000122 00 02                  505 ret #0x00


The :   483 ;   main.c: 65: AUTO_INIT_SYSCLOCK(); - is just as DS says for IHRC + sysclock 1MHz

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 12, 2020, 10:45:41 am
which programmer version you use ? (firmware and software)

What does this

487 ;   main.c: 70: AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);
And forward do ??

(...)

It does a lot of magic w. accumulator a , but never saves it anywhere  - It just does that stuff , and then returns 0x00 in a.


It is placeholder for programmer. Before flashing, it search for that code, reads desired MHz, and voltage, and replace that code with calibration routine. After flashing programmer use that routine to calibrate clock (by measuring pin change frequency, and switching pin), after that, calibration value is written and most of calibration routine is overwritten with nop (with OTP you can clear bit but can't set bit)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 11:02:18 am

I just found the "Magic sequence explanation"
https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2184683/#msg2184683 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2184683/#msg2184683)

I'm using Tim's Lite Programmer

And  easypdkprog from git
Code: [Select]
easypdkprog -V
easypdkprog 1.2



So my programmer is supposed to do something magic wrt. calibration , i didn't know that before now (that i'm digging through the 40+ pages)

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 12, 2020, 11:09:00 am
I have tested blink example and for me it's working.

Led turn on for 1sec then turn off for 1sec giving period of 2 sec.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 11:29:06 am
That is strange...

I'm getting a bit more than 2 secs in blink time.


I used this command for dfu loading the programmer :
Code: [Select]
$ dfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -D EASYPDKPROG.bin
I have no idea what the -a parm does.



I soldered the Programer MCU my self , i can't say that i didn't make an error - Still SMD beginner.
Any hints on what MCU legs the calibrate uses , i could trace them to the "socket"

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3084420/#msg3084420 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3084420/#msg3084420)

It might be an idea for the programmer sw. to write what calibration timing values it measured , and what calibration byte it wrote to the MCU.

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 12, 2020, 11:48:17 am
From where did you get easy-pdk-programmer-software ?

Get latest development branch, compile it and flash programmer.
note that there is EASYPDKPROG.dfu not EASYPDKPROG.bin
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 12, 2020, 12:06:41 pm
I'll give the DFU version a go

It's this one correct ?
https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Firmware (https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Firmware)
git clone https://github.com/free-pdk/easy-pdk-programmer-software.git (https://github.com/free-pdk/easy-pdk-programmer-software.git)


But i just noted this

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2660004/#msg2660004 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2660004/#msg2660004)
https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2660682/#msg2660682 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg2660682/#msg2660682)

I have 100nF across VDD+GND like Ali , seems like it could be a bad thing , during programming.

Did program the programmer w. the dfu

Code: [Select]
$ dfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -D EASYPDKPROG.dfu
dfu-util 0.9

Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc.
Copyright 2010-2016 Tormod Volden and Stefan Schmidt
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Opening DFU capable USB device...
ID 0483:df11
Run-time device DFU version 011a
Claiming USB DFU Interface...
Setting Alternate Setting #0 ...
Determining device status: state = dfuERROR, status = 10
dfuERROR, clearing status
Determining device status: state = dfuIDLE, status = 0
dfuIDLE, continuing
DFU mode device DFU version 011a
Device returned transfer size 2048
DfuSe interface name: "Internal Flash  "
Downloading to address = 0x08000000, size = 29068
Download [=========================] 100%        29068 bytes
Download done.
File downloaded successfully

Still getting 2 sec between blinks.

Might try to remove the 100nF   

Removed the 100nF across the suppply lines on the PADA , didn't help.

Still ticks w 2 sec intervals.


I have just resoldered the SPI side of the Programmer MCU , all looks ok.

Still 2 Sec intervals

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on July 12, 2020, 07:06:19 pm
I have written a "Digital I/O" and "Interrupts" section for the tutorial at https://free-pdk.github.io/tutorial (https://free-pdk.github.io/tutorial).

I currently envision the tutorial page as the knowledge database for both the Easy PDK Programmer and using SDCC to program the µCs.

Since I have only started using Padauk µCs a couple of days ago, I obviously don't have as much experience and knowledge when it comes to all of the little details.
If some of you have some time, it would be super cool if you could also help by extending the tutorial.
Adding new content to the tutorial is as easy as clicking "Edit this page on GitHub" at the bottom of the page then editing the markdown file.

I think that currently "any content is better than no content": Even if you don't have used all the, for example, ADC functionality, writing a section about the basic ADC functionality and caveats you experienced already is a great start.

Below are two examples of behavior that I personally didn't know about up until now. This is exactly the kind of stuff that is great for the tutorial IMHO.


The data sheet is also right... Usually PADAUK initializes the default values inside of the startup code they insert when you use the PADAUK IDE.
Since you use your own assembler / compiler you have to re-create the startup code and initializations.
BTW: PADAUK startup code wastes up to 10% of the valuable code memory.

Anyway, a good practice is to always set the complete value yourself.

JS

which programmer version you use ? (firmware and software)

What does this

487 ;   main.c: 70: AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);
And forward do ??

(...)

It does a lot of magic w. accumulator a , but never saves it anywhere  - It just does that stuff , and then returns 0x00 in a.


It is placeholder for programmer. Before flashing, it search for that code, reads desired MHz, and voltage, and replace that code with calibration routine. After flashing programmer use that routine to calibrate clock (by measuring pin change frequency, and switching pin), after that, calibration value is written and most of calibration routine is overwritten with nop (with OTP you can clear bit but can't set bit)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 12, 2020, 10:55:40 pm
I'll give the DFU version a go

It's this one correct ?
https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Firmware (https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Firmware)
git clone https://github.com/free-pdk/easy-pdk-programmer-software.git (https://github.com/free-pdk/easy-pdk-programmer-software.git)

...

Did program the programmer w. the dfu

Code: [Select]
$ dfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -D EASYPDKPROG.dfu
dfu-util 0.9

Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc.
Copyright 2010-2016 Tormod Volden and Stefan Schmidt
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Opening DFU capable USB device...
ID 0483:df11
Run-time device DFU version 011a
Claiming USB DFU Interface...
Setting Alternate Setting #0 ...
Determining device status: state = dfuERROR, status = 10
dfuERROR, clearing status
Determining device status: state = dfuIDLE, status = 0
dfuIDLE, continuing
DFU mode device DFU version 011a
Device returned transfer size 2048
DfuSe interface name: "Internal Flash  "
Downloading to address = 0x08000000, size = 29068
Download [=========================] 100%        29068 bytes
Download done.
File downloaded successfully

Still getting 2 sec between blinks.

...

I have just resoldered the SPI side of the Programmer MCU , all looks ok.

Still 2 Sec intervals

bingo600, it definitely sounds like you are not getting a successful calibration, and that is most likely why the timing is off.

As kaweksl has already indicated, this is most likely because the free-pdk-examples currently require the 'development' branch of the easy-pdk-programmer-software for successful calibration.  The calibration routines were changed compared to the previously released version (i.e. master).

You seem to have found the correct development branch, but it is unclear if you have actually re-complied the firmware and software.  Both are needed.  You can't just use the .dfu firmware from the development branch, as it hasn't been updated yet.  And, the easypdkprog software needs to be re-compiled as well.  You can't just use the previous 1.2 release.

When using the re-compiled .dfu firmware and the re-compiled easypdkprog you should get output like this (after running make program):
Code: [Select]
easypdkprog -n PFS154 write .output/BlinkLED_WithIRQ_PFS154.ihx
Erasing IC... done.
Writing IC (170 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 997283Hz (0x84)  done.

If you are not seeing those last two lines, something is off, and the IC is not properly calibrated.

If it still isn't working after making sure you are using re-compiled firmware and software, can you post the results of running make program so we can troubleshoot further?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 13, 2020, 12:16:12 pm
You may download my assembler and I wrote a small tutorial for it.
http://www.endresz.eu/padauk/padauk.html (http://www.endresz.eu/padauk/padauk.html)

Hope you will find it usefull!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 13, 2020, 02:44:53 pm
bingo600, it definitely sounds like you are not getting a successful calibration, and that is most likely why the timing is off.

As kaweksl has already indicated, this is most likely because the free-pdk-examples currently require the 'development' branch of the easy-pdk-programmer-software for successful calibration.  The calibration routines were changed compared to the previously released version (i.e. master).

You seem to have found the correct development branch, but it is unclear if you have actually re-complied the firmware and software.  Both are needed.  You can't just use the .dfu firmware from the development branch, as it hasn't been updated yet.  And, the easypdkprog software needs to be re-compiled as well.  You can't just use the previous 1.2 release.

When using the re-compiled .dfu firmware and the re-compiled easypdkprog you should get output like this (after running make program):
Code: [Select]
easypdkprog -n PFS154 write .output/BlinkLED_WithIRQ_PFS154.ihx
Erasing IC... done.
Writing IC (170 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 997283Hz (0x84)  done.

If you are not seeing those last two lines, something is off, and the IC is not properly calibrated.

If it still isn't working after making sure you are using re-compiled firmware and software, can you post the results of running make program so we can troubleshoot further?


Yesssss

Did a new Pull
Seems like Devel & Master has been "alligned"

I'm not a GIT Guru - is the below url correct for a "Git clone" , or should i have used some kind of tag to get devel ??
This devel
https://github.com/free-pdk/easy-pdk-programmer-software/tree/development

Has this as git chekout (no devel in the name)
https://github.com/free-pdk/easy-pdk-programmer-software.git

Well

My git pull as of today @16:15
Code: [Select]
git pull
remote: Enumerating objects: 5, done.
remote: Counting objects: 100% (5/5), done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 5 (delta 2), reused 5 (delta 2), pack-reused 0
Unpacking objects: 100% (5/5), done.
From https://github.com/free-pdk/easy-pdk-programmer-software
   3a557cc..78983e5  master      -> origin/master
   be5ea01..78983e5  development -> origin/development
 * [new tag]         1.3         -> 1.3
Updating 3a557cc..78983e5
Checking out files: 100% (153/153), done.

My Firmware make
Code: [Select]
arm-none-eabi-size build/EASYPDKPROG.elf
   text    data     bss     dec     hex filename
  33176     488   13088   46752    b6a0 build/EASYPDKPROG.elf
arm-none-eabi-objcopy -O binary -S build/EASYPDKPROG.elf build/EASYPDKPROG.bin
cp build/EASYPDKPROG.bin build/EASYPDKPROG.dfu
dfu-suffix -v 0483 -p df11 -a build/EASYPDKPROG.dfu
dfu-suffix (dfu-util) 0.9

Copyright 2011-2012 Stefan Schmidt, 2013-2014 Tormod Volden
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Suffix successfully added to file

My dfu programming
Code: [Select]
$ dfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -D EASYPDKPROG.dfudfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -D EASYPDKPROG.dfu
dfu-util 0.9

Copyright 2005-2009 Weston Schmidt, Harald Welte and OpenMoko Inc.
Copyright 2010-2016 Tormod Volden and Stefan Schmidt
This program is Free Software and has ABSOLUTELY NO WARRANTY
Please report bugs to http://sourceforge.net/p/dfu-util/tickets/

Opening DFU capable USB device...
ID 0483:df11
Run-time device DFU version 011a
Claiming USB DFU Interface...
Setting Alternate Setting #0 ...
Determining device status: state = dfuERROR, status = 10
dfuERROR, clearing status
Determining device status: state = dfuIDLE, status = 0
dfuIDLE, continuing
DFU mode device DFU version 011a
Device returned transfer size 2048
DfuSe interface name: "Internal Flash  "
Downloading to address = 0x08000000, size = 33664
Download [=========================] 100%        33664 bytes
Download done.
File downloaded successfully


And Yipieee ..... Calibrating  ;D ;D ;D
Code: [Select]
$ make clean program
rm -r -f .build .output
sdcc -mpdk14 -c --std-sdcc11 --fverbose-asm --opt-code-size -DPFS154 -DF_CPU=1000000 -DTARGET_VDD_MV=4000 -I. -I../include -o .build/main.rel main.c
sdar -rc .build/lib.lib
sdcc -mpdk14 --out-fmt-ihx -o .output/BlinkLED_WithIRQ_PFS154.ihx .build/main.rel .build/lib.lib
makebin -p .output/BlinkLED_WithIRQ_PFS154.ihx .output/BlinkLED_WithIRQ_PFS154.bin
---------- Segments ----------
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
HEADER1                             00000000    00000002 =           2. bytes (ABS,CON)
HEADER3                             00000000    00000010 =          16. bytes (ABS,CON)
PREG2                               00000000    00000002 =           2. bytes (ABS,CON)
RSEG0                               00000000    00000002 =           2. bytes (ABS,CON)
DATA                                00000002    00000015 =          21. bytes (REL,CON)
HOME                                00000022    00000002 =           2. bytes (REL,CON)
GSINIT                              00000024    00000014 =          20. bytes (REL,CON)
GSFINAL                             00000038    00000002 =           2. bytes (REL,CON)
CODE                                0000003A    00000124 =         292. bytes (REL,CON)
SSEG                                FFFFFFFF    00000001 =           1. bytes (REL,CON)
------------------------------
Size of BlinkLED_WithIRQ_PFS154.bin: 350 bytes
easypdkprog -n PFS154 write .output/BlinkLED_WithIRQ_PFS154.ihx
Erasing IC... done.
Writing IC (175 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 997066Hz (0x84)  done.


First time i ever saw Calibrating , when programming.

I have no idea what i did wrong , besides not specifying some magic git command on checkout.
And prob. being saved by master now updated to development.

A big thanx to @kaweksi and especially to @serisman for posting something usefull as the : Calibrating lines in the  output.
And thanx Tim for sending me to "Lite programmers" , and to JS... for making the website & examples.
And to all the others contributing to this , and SDCC.

But what did i do wrong ???
I never used the precompiled dfu , and made everything from source , even SDCC (That i in desparation now have installed in 3 versions , the 4.0 prebuilt , a Snapshot , and my own build from July-11) easy to switch if you use a symlink as the "Base dir".


Edit: easypdkprog still shows 1.2
Code: [Select]
$ easypdkprog -V
easypdkprog 1.2

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 13, 2020, 03:00:03 pm
Did a new Pull
Seems like Devel & Master has been "alligned"

Yes, to help alleviate all the confusion, JS just released version 1.3 to master a few hours ago, which includes all of the development changes.

Quote
I'm not a GIT Guru - is the below url correct for a "Git clone" , or should i have used some kind of tag to get devel ??
This devel
https://github.com/free-pdk/easy-pdk-programmer-software/tree/development

Has this as git chekout (no devel in the name)
https://github.com/free-pdk/easy-pdk-programmer-software.git

Well, git clone pulls down the repository with all the branches, so there isn't a different url per branch.
To change to a different branch you need to use the git checkout <branch> command (after pulling down the repo)

Quote
And Yipieee ..... Calibrating  ;D ;D ;D
Code: [Select]
$ make clean program
rm -r -f .build .output
sdcc -mpdk14 -c --std-sdcc11 --fverbose-asm --opt-code-size -DPFS154 -DF_CPU=1000000 -DTARGET_VDD_MV=4000 -I. -I../include -o .build/main.rel main.c
sdar -rc .build/lib.lib
sdcc -mpdk14 --out-fmt-ihx -o .output/BlinkLED_WithIRQ_PFS154.ihx .build/main.rel .build/lib.lib
makebin -p .output/BlinkLED_WithIRQ_PFS154.ihx .output/BlinkLED_WithIRQ_PFS154.bin
---------- Segments ----------
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
HEADER1                             00000000    00000002 =           2. bytes (ABS,CON)
HEADER3                             00000000    00000010 =          16. bytes (ABS,CON)
PREG2                               00000000    00000002 =           2. bytes (ABS,CON)
RSEG0                               00000000    00000002 =           2. bytes (ABS,CON)
DATA                                00000002    00000015 =          21. bytes (REL,CON)
HOME                                00000022    00000002 =           2. bytes (REL,CON)
GSINIT                              00000024    00000014 =          20. bytes (REL,CON)
GSFINAL                             00000038    00000002 =           2. bytes (REL,CON)
CODE                                0000003A    00000124 =         292. bytes (REL,CON)
SSEG                                FFFFFFFF    00000001 =           1. bytes (REL,CON)
------------------------------
Size of BlinkLED_WithIRQ_PFS154.bin: 350 bytes
easypdkprog -n PFS154 write .output/BlinkLED_WithIRQ_PFS154.ihx
Erasing IC... done.
Writing IC (175 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 997066Hz (0x84)  done.


First time i ever saw Calibrating , when programming.

Yay!  I'm glad you got it working!

Quote
I have no idea what i did wrong , besides not specifying some magic git command on checkout.
And prob. being saved by master now updated to development.

But what did i do wrong ???

My guess is it was a combination of potentially not actually being on the development branch, and possibly not actually re-compiling the easypdkprog software.

Quote
Edit: easypdkprog still shows 1.2
Code: [Select]
$ easypdkprog -V
easypdkprog 1.2

I'll have to check that out later.  Possibly JS missed a release step?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 13, 2020, 03:00:27 pm
Code: [Select]
./easypdkprog -vgives pc side software version

to get hw programmer version use
Code: [Select]
./easypdkprog --verbose probegives
Quote
Searching programmer... found: /dev/ttyACM0
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3 Protocol:1.3
Probing IC... Nothing found.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 13, 2020, 03:06:15 pm
Improvement for output of  easypdkprog -V
easypdkprog 1.2

$ git rev-parse HEAD
78983e5aee2ab4bc16628405a0da99ca290f9af3

Or
$ git log -1
commit 78983e5aee2ab4bc16628405a0da99ca290f9af3 (HEAD -> master, tag: 1.3, origin/master, origin/development, origin/HEAD)

Could you in the makefile run a:  git rev-parse HEAD , save it in a "GIT_VER"
Then insert a -DGIT_BUILD=$GIT_VER  , and use that GIT_BUILD as a string in the -V output ?

That could come in handy , when noobs like me don't know how to checkout development via git ?

easypdkprog -V
easypdkprog 1.2 - Git: 78983e5aee2ab4bc16628405a0da99ca290f9af3


All of the above git commands supplied by "Google" , i'm still at git clone & git pull  level.
SVN is my daily tool.

/Bingo



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 13, 2020, 03:18:04 pm
Edit: easypdkprog still shows 1.2
Code: [Select]
$ easypdkprog -V
easypdkprog 1.2

I'll have to check that out later.  Possibly JS missed a release step?

Yeah, it looks like the version number in the source code still needs to be updated (line 32):
https://github.com/free-pdk/easy-pdk-programmer-software/blob/master/easypdkprog.c
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 13, 2020, 03:22:02 pm
Improvement for output of  easypdkprog -V
easypdkprog 1.2

$ git rev-parse HEAD
78983e5aee2ab4bc16628405a0da99ca290f9af3

Or
$ git log -1
commit 78983e5aee2ab4bc16628405a0da99ca290f9af3 (HEAD -> master, tag: 1.3, origin/master, origin/development, origin/HEAD)

Could you in the makefile run a:  git rev-parse HEAD , save it in a "GIT_VER"
Then insert a -DGIT_BUILD=$GIT_VER  , and use that GIT_BUILD as a string in the -V output ?

That could come in handy , when noobs like me don't know how to checkout development via git ?

easypdkprog -V
easypdkprog 1.2 - Git: 78983e5aee2ab4bc16628405a0da99ca290f9af3


All of the above git commands supplied by "Google" , i'm still at git clone & git pull  level.
SVN is my daily tool.

/Bingo

bingo600,

That sounds like a good suggestion.  Why don't you open a feature request (i.e. issue) on GitHub?

I would think the releases would still just use the release number, but branches could use a git commit or possibly the git branch name and git commit.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 13, 2020, 03:42:47 pm
That sounds like a good suggestion.  Why don't you open a feature request (i.e. issue) on GitHub?

Done #45

Edit: I switched to development

Code: [Select]
$ git checkout development

Code: [Select]
$ git log -1
commit 78983e5aee2ab4bc16628405a0da99ca290f9af3 (HEAD -> development, tag: 1.3, origin/master, origin/development, origin/HEAD, master)
Author: freepdk <free-pdk@users.noreply.github.com>
Date:   Mon Jul 13 11:18:15 2020 +0200

    update firmware binary


/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 13, 2020, 06:08:05 pm
JS is a fast guy , thanx  :-+

#45 has been done for easypdkprog

See
https://github.com/free-pdk/easy-pdk-programmer-software/issues/45#issuecomment-657677538

Code: [Select]
$ easypdkprog -V
easypdkprog 1.3-3-gef65826

I hope this will tell you experienced guyzz , that i'm using latest devel.

Then it should be fast to spot someone not building from devel or latest whatever.


Hope the tag will find it's way into the Firmware too , when time is.

Code: [Select]
$ easypdkprog probe --verbose
Searching programmer... found: /dev/ttyACM3
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3-3-gef65826 Protocol:1.3
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 13, 2020, 06:12:07 pm
You may download my assembler and I wrote a small tutorial for it.
http://www.endresz.eu/padauk/padauk.html (http://www.endresz.eu/padauk/padauk.html)

Hope you will find it usefull!

Nice! You should post it on Github so it is added to the project list.

I have to ask though: Have you tried SDASPDKxx, the assembler that comes with SDCC?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 13, 2020, 08:11:31 pm
Some home-made projects using pdk

Replacement for PFC8574, NanoPi Duo controlling 1602 LCD with i2c using python
[attach=1]

PMS150C-U06 as I2C relay controller , I can't find my SOT23 LDO's so had to glue sot223
[attach=2]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 13, 2020, 08:38:37 pm
Would this patch work for addin git vers to the firmware ??

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 13, 2020, 08:47:59 pm
Would this patch work for addin git vers to the firmware ??

The problem is not adding it to the Makefile. The problem is to add the correct tag to the autobuild process.

Right now when you create a tag on master the travis autobuild uses this tag to include it into the release.
Since the firmware is not built with the autobuild right now there is no way to add the tag.

Example:
In future new master version is pushed and new tag 1.4 is added.
Then travis autobuild just compiles easypdkprog and creates the release
=> problem: firmware does not have new tag. Any previous (by hand) compiled firmware will have the old tag since the new tag is the trigger for autobuild.

=> solution: I need to add the firmware build to travis. this requires to add the arm build tools to the travis VM build process...

Have a look at ".travis.yml" and ".travis-build.sh".

And in case you did not have noticed there is a "build passed" badge on github. When you click on it you see the last autobuild: https://travis-ci.org/github/free-pdk/easy-pdk-programmer-software
and if you click on "Build History" there you see all autobuilds done: https://travis-ci.org/github/free-pdk/easy-pdk-programmer-software
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on July 14, 2020, 01:59:32 pm
@JS

Beautifull  :-+
Code: [Select]
$ easypdkprog -V
easypdkprog 1.3-10-gc5fabd3

Code: [Select]
$ easypdkprog probe --verbose
Searching programmer... found: /dev/ttyACM3
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3 (1.3-10-gc5fabd3)
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1


/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 14, 2020, 06:09:07 pm
You may download my assembler and I wrote a small tutorial for it.
http://www.endresz.eu/padauk/padauk.html (http://www.endresz.eu/padauk/padauk.html)

Hope you will find it usefull!

Nice! You should post it on Github so it is added to the project list.

I have to ask though: Have you tried SDASPDKxx, the assembler that comes with SDCC?

I only tried to write inline asm code in SDCC and I used the naked function keyword but still resulted a lot of extra asm code. I was unable to find any method to write code only in asm so I wrote my own assembler.

I'm working on the Github page.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 14, 2020, 06:24:51 pm
I made this: https://github.com/NetNickE/assembler-for-padauk (https://github.com/NetNickE/assembler-for-padauk)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 14, 2020, 06:37:31 pm
You may download my assembler and I wrote a small tutorial for it.
http://www.endresz.eu/padauk/padauk.html (http://www.endresz.eu/padauk/padauk.html)

Hope you will find it usefull!

Nice! You should post it on Github so it is added to the project list.

I have to ask though: Have you tried SDASPDKxx, the assembler that comes with SDCC?

I only tried to write inline asm code in SDCC and I used the naked function keyword but still resulted a lot of extra asm code. I was unable to find any method to write code only in asm so I wrote my own assembler.

I'm working on the Github page.

I used full assembler when SDCC was still in a very early state. See here for example: https://github.com/cpldcpu/SimPad/tree/6f3a2bbe980e9122dc814abd942b395621b8c02d/PFS154Blinky (https://github.com/cpldcpu/SimPad/tree/6f3a2bbe980e9122dc814abd942b395621b8c02d/PFS154Blinky)

Not sure if this still works with the current version. I will look into adding some pure assembler examples again.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on July 14, 2020, 09:04:26 pm
I was unable to find any method to write code only in asm so I wrote my own assembler.

The Padauk assemblers that are part of SDCC are separate executables (as are all of them for other supported platforms): sdaspdk13, sdaspdk14, and sdaspdk15.

Code: [Select]
sdas Assembler V02.00 + NoICE + SDCC mods  (Padauk 14)


Copyright (C) 2012  Alan R. Baldwin
This program comes with ABSOLUTELY NO WARRANTY.

Usage: [-Options] file
Usage: [-Options] outfile file1 [file2 file3 ...]
  -d   Decimal listing
  -q   Octal   listing
  -x   Hex     listing (default)
  -g   Undefined symbols made global
  -a   All user symbols made global
  -b   Display .define substitutions in listing
  -bb  and display without .define substitutions
  -c   Disable instruction cycle count in listing
  -j   Enable NoICE Debug Symbols
  -y   Enable SDCC  Debug Symbols
  -l   Create list   file/outfile[.lst]
  -o   Create object file/outfile[.rel]
  -s   Create symbol file/outfile[.sym]
  -p   Disable automatic listing pagination
  -u   Disable .list/.nlist processing
  -w   Wide listing format for symbol table
  -z   Disable case sensitivity for symbols
  -f   Flag relocatable references by  `   in listing file
  -ff  Flag relocatable references by mode in listing file
  -I   Add the named directory to the include file
       search path.  This option may be used more than once.
       Directories are searched in the order given.

The macro assembler that's part of SDCC is basically a fork of the ASxxxx cross-assembler. You can find documentation for it here: https://shop-pdp.net/ashtml/asxxxx.php

(Note that the main-line ASxxxx doesn't support Padauk micros, though. I don't believe anything has ever been 'back-ported' from SDCC.)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 15, 2020, 04:11:12 pm
Some home-made projects using pdk

Replacement for PFC8574, NanoPi Duo controlling 1602 LCD with i2c using python
(Attachment Link)

PMS150C-U06 as I2C relay controller , I can't find my SOT23 LDO's so had to glue sot223
(Attachment Link)

Thanks for sharing!

I assume the source code is in your https://github.com/kaweksl/pdk-codebucket (https://github.com/kaweksl/pdk-codebucket) repo?

That LCD adapter is similar to a project I had in mind.  But, why emulate the PCF8574 i2c extender when you could have a much more efficient/faster protocol that directly controls the LCD?  If I remember correctly, the PCF8574 requires a lot of overhead, specifically to properly toggle the LCD's EN line.

Edit:  Ok, I just looked at your source code, and it looks like your goal is a (mostly) compatible PCF8574 i2c expander, and not just a lcd driver.  This also gives the benefit of Arduino LiquidCrystal_I2C compatibility without introducing yet another new library.  So, it makes more sense why you are not using a more efficient protocol.  I am still interested in a more optimized version for myself and will work on that when I have time.

By the way, take a look at this library sometime: https://bitbucket.org/fmalpartida/new-liquidcrystal/wiki/Home
There are optimizations and performance tests showing i2c being pretty slow.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 15, 2020, 06:41:31 pm
That LCD adapter is similar to a project I had in mind.  But, why emulate the PCF8574 i2c extender when you could have a much more efficient/faster protocol that directly controls the LCD?  If I remember correctly, the PCF8574 requires a lot of overhead, specifically to properly toggle the LCD's EN line.

When developing i2c slave it was easy to compare and debug against PCF8574, also i could see "effect".

I assume the source code is in your https://github.com/kaweksl/pdk-codebucket (https://github.com/kaweksl/pdk-codebucket) repo?
Mostly same, needed to add some peephole rules since pdk13 has less instructions, also i switched from pin change interrupt to comparator interrupt, since pms150c-u6 don't have pin change interrupt, also added i2c address selection via external resistor value.

EDIT:
For me whole point of i2c is to save pins on master uc, reduce wires, speed has low priority. Also liquidcrystal_i2c library is not using PCF8574 sequential write (not sending address every byte) , which could speed up things.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 15, 2020, 07:55:47 pm
For me whole point of i2c is to save pins on master uc, reduce wires, speed has low priority. Also liquidcrystal_i2c library is not using PCF8574 sequential write (not sending address every byte) , which could speed up things.

Oh yes, I completely agree that i2c is more about saving pins than speed.  But, if it can do both, why not.

I was just pointing out that if the goal is an i2c lcd adapter, there are faster / more efficient ways to drive an lcd over i2c than what the PCF8574 i2c expander allows (even with sequential write).

If I remember correctly, the PCF8574 is wired up using 4-bit mode, which requires 2 transfers per command/data byte.  But, I believe it also needs a second transfer per nibble to toggle the EN line, so that is at least 4 i2c transfers per lcd command/data byte.  Without sequential mode, that doubles again to 8 i2c transfers per command/data byte.  With a 14 or 16 pin Padauk, there should be enough I/Os for 8-bit mode along with the normal control lines (RS, RW, EN).  So, you could drive it much faster, almost down to 1 transfer per command/data byte (would depend on specific protocol used... a 'dumb' protocol could use 2 transfers, one to control RS, one for the actual command/data... a 'smart'er protocol could get slimmer by having a virtual command byte transfer optionally followed up by one or more data bytes... i.e. write data command followed by bytes to write, which would then be terminated by a null/zero data byte or i2c stop).  This would also optionally allow to read from the lcd instead of just write to it, meaning the status bit could be used to know when it is ok to send the next command/byte instead of relying on delays that have to be long enough for the worst case + some extra padding.  The disadvantage would be slightly more complex code in the padauk ic and need for an additional client library, but as an advantage, the additional client library should be really simple and smaller than any existing client library.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 15, 2020, 08:28:26 pm
This is where the lite r1 programmers are stuck :( Looks like JLCPCBs Europaket is not such a good idea after all. I guess one of the packages they included created a customs issue...

[attachimg=1]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 15, 2020, 11:16:40 pm

I was just pointing out that if the goal is an i2c lcd adapter, there are faster / more efficient ways to drive an lcd over i2c than what the PCF8574 i2c expander allows (even with sequential write).
(...)
Creating dedicated i2c bridge would make sense (for me) only if it would take "high level commands", like setCursor, backlight, printascii,  and push it to lcd. But for that im not sure if we have enough idle time between transferring i2c bytes to do that on the fly, and we can't do parallel processing. So that would require to use:
- buffer and doing conversion after i2c frame, which would require some 'busy' time after each frame, reducing speed
- using clock i2c stretching, which may not be compatible with some masters, also reducing speed
- any ideas ?

And to be honest i have no idea how to drive 1602 :P

This is where the lite r1 programmers are stuck :( Looks like JLCPCBs Europaket is not such a good idea after all. I guess one of the packages they included created a customs issue...

Is lite version made in easyeda too ?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 04:20:41 am
Here's a fun little project I whipped up on a breadboard today: https://github.com/serisman/pdk-continuity-tester (https://github.com/serisman/pdk-continuity-tester)

It is a standalone continuity tester, that uses the Comparator to test for continuity, and has an aggressive battery saving mode (< 0.5 uA while sleeping).

It is a port to the Padauk MCUs of an original project by David Johnson-Davies for the ATtiny85:

I have used the original ATtiny85 version for a few years, and have found it quite useful.  It frees up having to pull out a multimeter to do quick tests for continuity.

I've tested it on the PFS154 and PFS173, but it should also run on (at least) the PMS150C, PMS152, PMS154C as well.

It can even run on the 6-pin variants, and uses less than 100 words of code, and only 2 bytes of ram!

Eventually I will create and share a custom PCB for it as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 16, 2020, 04:38:48 am
Here's a fun little project I whipped up on a breadboard today: https://github.com/serisman/pdk-continuity-tester (https://github.com/serisman/pdk-continuity-tester)

It is a standalone continuity tester, that uses the Comparator to test for continuity, and has an aggressive battery saving mode (< 0.5 uA while sleeping).


That's a really neat project! Honestly, I would not have thought about using a MCU for this in the first place, so it is a good example for a use case of ultra-low-cost MCUs.

I wonder about the usage of the pin change for wakeup: This somehow implies that there is a trickle charge to pull the pin up while the MCU is asleep. So this is valid for both the Padauk MCUs and the ATtiny85?

Btw, one could probably  reduce active power consumption by making everything interrupt driven. But I guess that is inconsequential.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 04:56:16 am
That's a really neat project! Honestly, I would not have thought about using a MCU for this in the first place, so it is a good example for a use case of ultra-low-cost MCUs.

Agreed!  And this is probably cheaper than (most) other approaches as well!  This can run on the 6/8-pin PMS150C (~$0.03) making it cost about the same as a few passives.  The Buzzer/Battery are the most expensive components on the build.

Quote
I wonder about the usage of the pin change for wakeup: This somehow implies that there is a trickle charge to pull the pin up while the MCU is asleep. So this is valid for both the Padauk MCUs and the ATtiny85?

Yes, the pull-up on the Probe pin is enabled, as well as the wake-up (i.e. PADIER) for that pin.  I have measured ~0.2-0.3 uA @ 3V while sleeping (using my Keysight 34465A 6.5 digit multimeter).  For a while I was measuring 1000x more sleep current until I also turned off wake-up for all the other pins (i.e. PBDIER).  The ATtiny85 version uses about the same in sleep mode.

Quote
Btw, one could probably  reduce active power consumption by making everything interrupt driven. But I guess that is inconsequential.

Not sure how interrupts would actually help here.  I suppose I could remove the idle counter if active power consumption really mattered (i.e. only keep the MCU awake in order to drive the Buzzer/LED while there is continuity), but 99.999% of the active power consumption is going to the Buzzer and power indicator LED.  The MCU itself only uses 0.3 mA (or so) while awake anyway (1MHz @ ~3V).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 16, 2020, 05:01:57 am

Quote
Btw, one could probably  reduce active power consumption by making everything interrupt driven. But I guess that is inconsequential.

Not sure how interrupts would actually help here.  I suppose I could remove the idle counter if active power consumption really mattered (i.e. only keep the MCU awake in order to drive the Buzzer/LED while there is continuity), but 99.999% of the active power consumption is going to the Buzzer and power indicator LED.  The MCU itself only uses 0.3 mA (or so) while awake anyway (1MHz @ ~3V).

Well, 0.5-1 mA should be enough for the LED, so it is more like 50-70%. But as mentioned, this should be inconsequential.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 05:06:33 am
Well, 0.5-1 mA should be enough for the LED, so it is more like 25-40%. But as mentioned, this should be inconsequential.

A good portion of the active current is actually going to the Buzzer (probably 80% or so), and I don't really want to make that any quieter.  I measured around 10 mA (@3V) with everything active, which is about the same as the ATtiny85 version.  That could probably be optimized a bit (i.e. use slower ILRC instead of IHRC, dimmer power LED, quieter Buzzer), but certainly with diminishing returns.

EDIT:  Yeah, I just verified that without the Buzzer connected, the active current is less than 1 mA (LED and MCU).  So, currently the buzzer is using 90+% of the active current.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 16, 2020, 05:16:39 am
Well, 0.5-1 mA should be enough for the LED, so it is more like 25-40%. But as mentioned, this should be inconsequential.

A good portion of the active current is actually going to the Buzzer (probably 80% or so), and I don't really want to make that any quieter.  I measured around 10 mA (@3V) with everything active, which is about the same as the ATtiny85 version.  That could probably be optimized a bit (i.e. use slower ILRC instead of IHRC, dimmer power LED, quieter Buzzer), but certainly with diminishing returns.

EDIT:  Yeah, I just verified that without the Buzzer connected, the active current is less than 1 mA (LED and MCU).  So, currently the buzzer is using 90+% of the active current.

So one should introduce a "quiet" mode, for power users who don't have a lot of power available :) (no, not serious)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 05:20:52 am
So one should introduce a "quiet" mode, for power users who don't have a lot of power available :) (no, not serious)

 :-DD

For reference... My original ATtiny85 version (very similar power consumption numbers) still has the original (used) CR2032 that I installed over a year ago and have used intermittently since.  It still measures 3.1V.  So, I don't think active power consumption it is an issue at all.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 16, 2020, 05:31:24 am
Here is a challenge: Operate it from a single LR41 cell (1.5V).

I was quite suprised to find that there are very few MCUs for less than 1.8V out there. The only one I found is MSP430L.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 05:37:50 am
Here is a challenge: Operate it from a single LR41 cell (1.5V).

Yeah, that's going to need a booster, or better yet, just run two in series.

These Padauk MCUs all seem to need about 2V (+/- 0.2V) minimum to operate.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 16, 2020, 08:26:21 am
I measured the voltage on PFS154 digital output, when I output low level I measure 0.47V and 4.56V is the high level. PFS154 is powerred from 5V USB (actully 5.02V). So the low is pretty high, the high is pretty low.
Most of the digital IC will sense this voltage levels correct but on PIC and Atmel processors the low is very close to 0V and the high is the supply voltage.

Are there any configuration to get better results?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 16, 2020, 08:39:25 am
I measured the voltage on PFS154 digital output, when I output low level I measure 0.47V and 4.56V is the high level. PFS154 is powerred from 5V USB (actully 5.02V). So the low is pretty high, the high is pretty low.
Most of the digital IC will sense this voltage levels correct but on PIC and Atmel processors the low is very close to 0V and the high is the supply voltage.

Are there any configuration to get better results?

Did you load the output in any way? But anywys, the GPIO in the PFS are unusually weak. Probably a way to save die area and hence cost.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 16, 2020, 08:44:44 am
Here's a fun little project I whipped up on a breadboard today: https://github.com/serisman/pdk-continuity-tester (https://github.com/serisman/pdk-continuity-tester)

Nice little project. Thanks for sharing.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 16, 2020, 08:59:38 am
I measured the voltage on PFS154 digital output, when I output low level I measure 0.47V and 4.56V is the high level. PFS154 is powerred from 5V USB (actully 5.02V). So the low is pretty high, the high is pretty low.
Most of the digital IC will sense this voltage levels correct but on PIC and Atmel processors the low is very close to 0V and the high is the supply voltage.

Are there any configuration to get better results?

According to CMOS and TTL specification (https://en.wikipedia.org/wiki/Logic_level) this is perfectly within the specified ranges:

CMOS: low: 0V to 1/3 VDD high: 2/3 VDD to VDD  (for 5V VDD this translates to low: 0V - 1.6V, high: 3.3V - 5V)
TTL: low: 0V to 0.8V  high: 2V to VCC (VCC = 5 V ±10%)

So your sentence "Most of the digital IC will sense this voltage levels correct" becomes... There might be some IC's (not compatible with CMOS or TTL specification) which might sense this voltage levels incorrect (which is also true for 99% of other ICs on market).

Anyway in case you want to play with the outputs on PFS154, look at the pull up registers PAPH and PBPH.
There is also a fuse value which you might want to try out: FUSE_IO_DRV_LOW  / FUSE_IO_DRV_NORMAL (I never played with this so any research on this from you will be appreciated. FUSE_IO_DRV_NORMAL is default which is used when you do not set the fuse).
You can set it in _sdcc_external_startup like this: EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_FAST|FUSE_IO_DRV_LOW); Have a look in programmer software Examples folder: calib-and-fuse-demo.c 
You also can specify the fuse as a command line argument to easypdkprog: --fuse=0x3EFD   (this value is for PFS154 only, and reflects: FUSE_SECURITY_OFF | FUSE_IO_DRV_LOW | FUSE_BOOTUP_FAST)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 16, 2020, 05:56:09 pm
Here's a fun little project I whipped up on a breadboard today: https://github.com/serisman/pdk-continuity-tester (https://github.com/serisman/pdk-continuity-tester)

Nice little project. Thanks for sharing.

JS

Thanks!

I just uploaded a schematic and PCB design for the 6-pin PMS150C.  (gerbers available, and already shared on OSHPARK: https://oshpark.com/shared_projects/XcWQiX7z)

[attach=1]

This PCB is meant to be attached to the bottom of a ~12mm Piezo Buzzer, where the SMD parts are first soldered to the board, and are underneath the buzzer. There are through-holes for the two probe connections, and pads on the back for the battery connections. 2x LR44 battery cells in series would pair nicely with this PCB, as they are a good voltage match, and are approximately the same diameter (meaning the whole thing can be heat shrunk together for a miniature continuity tester).

[attach=2]
[attach=3]
[attach=4]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 20, 2020, 01:01:10 am
I finally designed a PCB for my Padauk based 7-segment digital clock.

I also moved the project to its own repository and added some README files:
https://github.com/serisman/pdk-digital-clock

It will take about two weeks before the PCBs are delivered to me, but I feel pretty confident in the design.  I've been running it on a breadboard for a few weeks now.

[attach=1]
[attach=4]
[attach=2]
[attach=3]

Feel free to suggest new 'features' or make pull requests with enhancements or bug fixes.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 20, 2020, 10:55:10 am
Does the PFS173-S20 really exist? It is not listed on LCSC nor on Alibaba. It's only in datasheet...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 20, 2020, 12:44:21 pm
Does the PFS173-S20 really exist? It is not listed on LCSC nor on Alibaba. It's only in datasheet...

Sure it exists and it is available in small quantities e.g. from Taobao:

https://item.taobao.com/item.htm?spm=a1z10.5-c.w4002-15889356058.11.4f019facMXA64B&id=598987867714

0.5 RMB / pcs - for 50pcs (apx. USD 3.58) + shipping.

The seller is trustworthy. I ordered several times from there.

BTW: There are some Taobao forwarders which will help you to ship the things from taobao.

Adventure time :-)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 21, 2020, 07:29:19 am
Quote
Sure it exists and it is available in small quantities e.g. from Taobao:

https://item.taobao.com/item.htm?spm=a1z10.5-c.w4002-15889356058.11.4f019facMXA64B&id=598987867714

0.5 RMB / pcs - for 50pcs (apx. USD 3.58) + shipping.

The seller is trustworthy. I ordered several times from there.

BTW: There are some Taobao forwarders which will help you to ship the things from taobao.

Adventure time :-)
How do you chat and contact with them?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 21, 2020, 01:32:27 pm
I did something wrong. Now all digital output goes down to 0V and up to 5V.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 21, 2020, 10:59:26 pm
Does the PFS173-S20 really exist? It is not listed on LCSC nor on Alibaba. It's only in datasheet...

Sure it exists and it is available in small quantities e.g. from Taobao:

https://item.taobao.com/item.htm?spm=a1z10.5-c.w4002-15889356058.11.4f019facMXA64B&id=598987867714

0.5 RMB / pcs - for 50pcs (apx. USD 3.58) + shipping.

The seller is trustworthy. I ordered several times from there.

BTW: There are some Taobao forwarders which will help you to ship the things from taobao.

Adventure time :-)

Which agent do you use ?
Did you tested those PMS132b in qfn ?

I have bought some PFC232, gonna try to play with second FFPA, if they arrive.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 22, 2020, 07:41:20 am
Hopefully I will be able to solve the project with PFS154-S16 which I already have. For now I only focus on PFS154 and PFS173 chip and I prefer S16 or S20 package because it is easy to solder. I can do QFN and others, I have a lot of experience in soldering but S16 is more convenient and faster. Anyway I will try to buy PFS173-S20 if possible. If not then PFS173-H20.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 26, 2020, 12:32:49 am
Hi all - first post!

I ordered the open source programmer PCB and I'm having trouble soldering the small components (my ego is writing cheques my eyesight can't cash...) which makes the resultant non-functional board difficult for me to troubleshoot. Is there any reason why the board can't be mostly through-hole (see attachment)? And if this is going to work:

I will keep soldering (I have 5 PCBs to trash in this experiment and I'm damn stubborn), but looking forward I was hoping that an old man version might be better suited to my needs. Thoughts and feedback appreciated!

OneCircuit
www.onecircuit.blogspot.com (http://www.onecircuit.blogspot.com)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 26, 2020, 08:40:51 am
Hi all - first post!

I ordered the open source programmer PCB and I'm having trouble soldering the small components (my ego is writing cheques my eyesight can't cash...) which makes the resultant non-functional board difficult for me to troubleshoot. Is there any reason why the board can't be mostly through-hole (see attachment)? And if this is going to work:
  • can all the SMD schottky diodes be replaced with 1N5817?
  • can the 47uF cap be electrolytic and therefore have polarity?
  • can the 6.8uH inductor be radial?
  • are there through-hole equivalents for BSS138 and BSS84 (basically just trying to limit the SMD stuff)
  • I've re-arranged the components for ease of use in putting the board together, but will the resultant long traces be a possible problem?
  • there are 5 holes on the board (1 and then 4 together) but I have no idea for what purpose!?

I will keep soldering (I have 5 PCBs to trash in this experiment and I'm damn stubborn), but looking forward I was hoping that an old man version might be better suited to my needs. Thoughts and feedback appreciated!

OneCircuit
www.onecircuit.blogspot.com (http://www.onecircuit.blogspot.com)

Most likely your PCB will NOT work.

You missed very basic things like placing decoupling caps as close as possible to the components they are intended for. E.g. the 4 x 100nF next to the processor are much to far away to have any effect.
Also the coil, the diode and the big decoupling caps for the dc-dc boost need to be as close as possible to the boost IC. Then you have traces at the very edge of the PCB which will be rejected from PCB manufacturer, ...
But the main problem is that you introduced a lot of power / ground loops since your traces are running back and forth all over the board (e.g. follow the 5V input from USB to see what I mean).
It looks like you just placed all components in a random way (maybe for easy soldering) ignoring any design requirements and then tried to put some traces.
This can work for simple schematics like a MCU + LED but this creates real problems with high frequency (several MHz) circuits like the DC-DC boost, USB, STM32, ...)

BTW: Your design also misses the reference to "free-pdk.github.io" Please don't forget to respect the open source license the original is released under:
=> https://github.com/free-pdk/easy-pdk-programmer-hardware/blob/master/LICENSE (https://github.com/free-pdk/easy-pdk-programmer-hardware/blob/master/LICENSE)   (CC-BY-SA-4.0)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 26, 2020, 08:44:30 am
If you can solder the STM32 chip then other components should be easy...

Anyway I also bought 5 pack of PCB and most other components because there was a minimum order of 5 of most of the parts but I don't need all of them.

If someone is interested to buy a fully assembled tested one PM me. Will send it from Hungary as registered priority mail. Hopefully it arrives faster to EU countries but the shipping is a bit more expensive then from China.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 26, 2020, 08:53:40 am
How do you chat and contact with them?

Which agent do you use ?

I do not have a specific agent I use. In the past I ordered and received the stuff in China directly when I was on business trips there. Right now it is complicated to travel so I used an agent (which seems to have stopped now).

Here is a pointer for agents: https://www.howtotao.com/best-taobao-agent/ (https://www.howtotao.com/best-taobao-agent/)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 26, 2020, 09:47:46 am
I ordered the open source programmer PCB and I'm having trouble soldering the small components (my ego is writing cheques my eyesight can't cash...) which makes the resultant non-functional board difficult for me to troubleshoot. Is there any reason why the board can't be mostly through-hole (see attachment)? And if this is going to work:

Besides the stability issues mentioned by JS, I would also like to point out that this does not really address the core of the issue. In my eyes, the three most difficult to assemble items are:


Changing all possible parts to THT will only address one of those. So people who have issues with SMD soldering will still encounter signficant challenges.

But anyways, don't feel discouraged from your project, who does not like to design PCBs? :)

One additional comment: The 1N5817 have a very high junction capacitance. The charge pump may not work with them.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 26, 2020, 10:26:59 am
Great feedback thanks! I pretty much knew my thought bubble would burst - I guess I would like to know if a through-hole version is possible? I'll shift some stuff around according to the suggestions and report back in a few days. Thanks for the heads up about the IP - as an ex patent examiner I should have been more aware of that!

On the plus side - my second SMD version had some small success - it recognised the PMS150C, but not the PFS154 or PFS173. It was unable to program any of them...

PMS150C:
easypdkprog probe
Probing IC... found.
TYPE:OTP RSP:0x285A0 VPP=4.50 VDD=2.00
IC is supported: PMS150C / PMS15A ICID:0xA16

Programming PMS150C:
make clean program
rm -r -f .build .output
sdcc -mpdk13 -c --std-sdcc11 --opt-code-size -DPMS150C -DF_CPU=1000000 -DTARGET_VDD_MV=4000 -I. -I../include -o .build/main.rel main.c
sdar -rc .build/lib.lib
sdcc -mpdk13 --out-fmt-ihx -o .output/BlinkLED_PMS150C.ihx .build/main.rel .build/lib.lib
makebin -p .output/BlinkLED_PMS150C.ihx .output/BlinkLED_PMS150C.bin
---------- Segments ----------
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
.  .ABS.                            00000000    00000000 =           0. bytes (ABS,CON)
HEADER1                             00000000    00000002 =           2. bytes (ABS,CON)
HEADER3                             00000000    00000010 =          16. bytes (ABS,CON)
PREG2                               00000000    00000002 =           2. bytes (ABS,CON)
RSEG0                               00000000    00000002 =           2. bytes (ABS,CON)
DATA                                00000002    00000007 =           7. bytes (REL,CON)
HOME                                00000022    00000002 =           2. bytes (REL,CON)
GSINIT                              00000024    00000014 =          20. bytes (REL,CON)
GSFINAL                             00000038    00000002 =           2. bytes (REL,CON)
CODE                                0000003A    00000074 =         116. bytes (REL,CON)
SSEG                                FFFFFFFF    00000001 =           1. bytes (REL,CON)
------------------------------
Size of BlinkLED_PMS150C.bin: 174 bytes
easypdkprog -n PMS150C write .output/BlinkLED_PMS150C.ihx
FPDK_ERROR: command ack failed / wrong icid
Makefile:63: recipe for target 'program' failed
make: *** [program] Error 252

PFS154 and PFS173:
easypdkprog probe
Probing IC... Nothing found.

If the PFS154 and PFS173 are not recognised, and nothing is able to be programmed - what would you recommend I swap out? Or should I just knuckle down and go for MKIII? I am getting better at SMD!

Take care,

One Circuit
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 26, 2020, 01:28:31 pm
Revision1 of the lite-programmer finally arrived from JLCPCB. I made a minor mistake in one resistor value, but everything else turned out nicely and the programmer is fully functional. There is plenty of space on the PCB due to switching to 0402.

The programmer is optimized to be fully assembled by JLCPCBs assembly service, only a few parts have to be added manually (button, USB, inductor, crystal, connectors).

I will prepare documentation on how to order an assembled programmer during the next days. I hope that finally provides a remedy for everyone who had issues obtaining a programmer.

I also have a few left-over boards - send a PM to me if your are interested.

[attach=1]

Also the break-out boards, that can be plugged into the programmer, arrived.

[attach=2]
[attach=3]



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on July 26, 2020, 02:08:22 pm
If the PFS154 and PFS173 are not recognised, and nothing is able to be programmed - what would you recommend I swap out? Or should I just knuckle down and go for MKIII? I am getting better at SMD!

This is actually rather strange, since the PMS150 is actually more critical. At least probing should work.

Have you checked voltages with "easypdkprogtest.exe"=?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 27, 2020, 08:02:14 am
Quote
Have you checked voltages with "easypdkprogtest.exe"=?

easypdkprogtest
vdd: 3.62   vpp: 3.62    (vref= 3.27) 

It looks like the 5V rail is not 5V but more like 1.9V. That can't be good - I have struggled the most with the USB connector so I'll keep working on that - but of course there might be a compromised component somewhere. My OpAmp measurements are way different to this:

Quote

Reference voltages when running easypdkprogtest:

                   +-------+
                   |   O   |
(DAC-VPP) 1.18V -> |5  P  4| <- -2.7V
          1.18V -> |6  A  3| <-  2.49V (DAC-VDD)
(VPP)      5.0V <- |7  M  2| <-  2.49V
          14.9V -> |8  P  1| ->  5.0V  (VDD)
                   |      .|
                   +-------+

       

More like this:

Reference voltages when running easypdkprogtest:


                   +-------+
                   |   O   |
(DAC-VPP)   -2V -> |5  P  4| <-  -6V
         -2.42V -> |6  A  3| <-  -0.78V (DAC-VDD)
(VPP)     0.32V <- |7  M  2| <-  -1.44V
          1.69V -> |8  P  1| ->  0.34V  (VDD)
                   |      .|
                   +-------+


I think MKIII is the way to go with lessons learned along the way... :-\

Take care,

OneCircuit

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daveatol on July 27, 2020, 08:39:15 am
Reference voltages when running easypdkprogtest:


                   +-------+
                   |   O   |
(DAC-VPP)   -2V -> |5  P  4| <-  -6V
         -2.42V -> |6  A  3| <-  -0.78V (DAC-VDD)
(VPP)     0.32V <- |7  M  2| <-  -1.44V
          1.69V -> |8  P  1| ->  0.34V  (VDD)
                   |      .|
                   +-------+


What's up with your 15V supply? It should be going to pin 8 of the opamp, and yours is apparently 1.69V. Is your dc-dc converter disabled, or faulty?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 27, 2020, 11:26:12 am
Quote
What's up with your 15V supply? It should be going to pin 8 of the opamp, and yours is apparently 1.69V. Is your dc-dc converter disabled, or faulty?

It's a mess for sure - I'm going to start again and hopefully have better success with MKIII.  :-//

Take care,

OneCircuit
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on July 28, 2020, 12:50:04 pm
In easypdkprog the --securefill option makes only sense at OTP MCUs. Am I right?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 28, 2020, 05:31:02 pm
Also the break-out boards, that can be plugged into the programmer, arrived.

Speaking of break-out / adapter boards... I designed some new ones a few days ago:


Gerber files are also available if interested, and I can post all the design files somewhere at some point as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on July 30, 2020, 09:55:42 am
Can we Port avr v-usb Library to Padauk?

https://www.obdev.at/products/vusb/index.html (https://www.obdev.at/products/vusb/index.html)

It's a bit-bang USB library for AVR's ^-^ >:D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on July 30, 2020, 12:56:43 pm
VUSB won't fit into most padauks as they are around 1K ROM and 80 B RAM.

Check CH552 it is low cost, has HW usb and requires only 2 caps to operate.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on July 30, 2020, 08:28:12 pm
VUSB won't fit into most padauks as they are around 1K ROM and 80 B RAM.

tim_ has a project from a few years ago (https://cpldcpu.wordpress.com/2014/03/19/%c2%b5-wire-usb-on-an-attiny-10/) (https://github.com/cpldcpu/u-wire) where he got a subset of the V-USB stack working on an ATtiny10 using 988 bytes of flash and 32 bytes of SRAM.

So, it might actually be possible to get something working on these Padauk MCUs.  It would probably require 'overclocking' and/or using the undocumented 16MHz sysclock mode.  Other than the novelty factor, I'm not sure how useful it would actually be, though.

Quote
Check CH552 it is low cost, has HW usb and requires only 2 caps to operate.

I agree, those are interesting (and inexpensive) MCUs, and have a USB/Serial bootloader so you don't even need a custom programmer.  Or, use the even smaller/cheaper CH551.  There are also the CH554/CH558/CH559 bigger brothers that even have USB host mode.  Being 8051 based, you can still use SDCC as well.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 01, 2020, 07:08:28 am
Quote
Check CH552 it is low cost, has HW usb and requires only 2 caps to operate.
If it can be done on a padauk, it would cost a lot less, It can be replaced for USB to UART.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 01, 2020, 09:20:35 am
VUSB won't fit into most padauks as they are around 1K ROM and 80 B RAM.

tim_ has a project from a few years ago (https://cpldcpu.wordpress.com/2014/03/19/%c2%b5-wire-usb-on-an-attiny-10/ (https://cpldcpu.wordpress.com/2014/03/19/%c2%b5-wire-usb-on-an-attiny-10/)) (https://github.com/cpldcpu/u-wire (https://github.com/cpldcpu/u-wire)) where he got a subset of the V-USB stack working on an ATtiny10 using 988 bytes of flash and 32 bytes of SRAM.

So, it might actually be possible to get something working on these Padauk MCUs.  It would probably require 'overclocking' and/or using the undocumented 16MHz sysclock mode.  Other than the novelty factor, I'm not sure how useful it would actually be, though.

Indeed! That was a fun project. It was even reposted by one of the AVR founders (I think Vergard), so it surprised some people that this is possible, i guess :)

My guess is that an implementation from scratch in assembler could be much smaller. The Padauk instruction set should be quite efficient in handling the bitwrangling needed for USB.

If you are out for an interesting challenge, go for it! I would recommend to get a logic analyzer with USB protocol analysis capability first. Also, this: https://www.beyondlogic.org/usbnutshell/usb1.shtml (https://www.beyondlogic.org/usbnutshell/usb1.shtml)

I have to second the comments regarding usefullness of software implementations, though. The USB protocoll is based on polling from the host (your PC), so any client has to be able to respond within microseconds all the time. The can be relaxed a bit using the tricks shown above, but regardless it will mean that any kind of firmware on your device has to be written around the USB protocol. I founds this a bit too limiting.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on August 01, 2020, 05:05:58 pm
Hello everyone. First post here! Apologies if this isn't the right place for this, but this thread seemed to be the most active place for discussing the Padauk OSH efforts.

I put in an order on LCSC for the parts list as given on the free-pdk hardware github, but now it's sitting in inquiry limbo. It looks like there's a couple items listed as "Backorder" with one even being listed as "Unavailable, please remove it." I'm new to LCSC, is there a way to replace these parts with possible equivalents in the order or will I have to start from a fresh order? I'm leery of making two orders given shipping costs.

Ironically, I got an email from OshPark that they'd upgraded my order to their super fast turnaround service for free, due to space on a panel... so now I'm going to get the blank boards way ahead of time!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 01, 2020, 05:13:18 pm
I finally designed a PCB for my Padauk based 7-segment digital clock.

I also moved the project to its own repository and added some README files:
https://github.com/serisman/pdk-digital-clock

It will take about two weeks before the PCBs are delivered to me, but I feel pretty confident in the design.  I've been running it on a breadboard for a few weeks now.

Feel free to suggest new 'features' or make pull requests with enhancements or bug fixes.

My PCBs were delivered yesterday, and I promptly built one up (used a OTP PMS152-S16):

Front (before installing 7-segment display):
[attach=1]

Back:
[attach=2]

Installed on monitor (and working):
[attach=3]


I am pretty happy with the results, and am calling this project done (at least for version 1).

I updated the github repo with a BOM for anyone interested.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 01, 2020, 11:35:28 pm
I had the same problem and had to split my order between LCSC and AliExpress. In the end the parts required for the programmer came from both suppliers at about the same time. The difficult part for me hasn’t been the acquisition of parts, but soldering those pesky SMD components (the USB connector is challenging). At this stage I’ve trashed two PCBs in the process, but the third one is looking good!

OneCircuit
www.onecircuit.blogspot.com (http://www.onecircuit.blogspot.com)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on August 02, 2020, 02:02:13 am
Thanks for the tip, bovineck. Unfortunately, I have to call my bank to approve the payment on AliEx for some reason, and the robot that answered my phone call curtly informed me that the office was closed and hung up on me!  :-DD   |O

Ah well. I'm being cheap on the shipping from LCSC so I've got plenty of time to sort it all out. Excited to dip into this Padauk stuff for real when it does! It's been on my radar since the original EEVBlog vid on it, but I'd always figured ATTiny85s were a better go-to until recently. I'm planning some things with lots and lots of blinkenlights and it felt wasteful to stuff the project full of Atmels when all those fancy features (and the reprogramming) weren't necessary for the design.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 02, 2020, 02:49:21 am
I use a prepaid debit card, load with cash at the P.O., then off to the interwebs for shopping. I too am looking forward to getting a working programmer. It’s been a journey, and my soldering skills have definitely improved! 🧐
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 03, 2020, 03:08:25 pm
I have a very nice hacking project with a commercial product using a PADAUK MCU coming soon.

Teaser:
000000011001001010000100100001000110010010000100100001001001010010000100
000000011001001010000100011001001000010010000100100001001001010010000100
000000011001001010000100100001001000010001100100100001001001010010000100
000000010101010110000100100001001000010010000100100001001001010010000100


8)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 05, 2020, 06:21:06 am
I am trying to implement tone function.
I am looking for a way to do microseconds delay (like delayMicroseconds() in Arduino). However, existing delay functions are either for milliseconds only or way too large and use all the SRAM.

Any help would be greatly appriciated!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on August 05, 2020, 08:55:03 am
Just execute a few nop instruction. You can put them into a function.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on August 05, 2020, 09:26:24 am
Quote
000000011001001010000100100001000110010010000100100001001001010010000100
000000011001001010000100011001001000010010000100100001001001010010000100
000000011001001010000100100001001000010001100100100001001001010010000100
000000010101010110000100100001001000010010000100100001001001010010000100
It's a beauty >:D ^-^
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 05, 2020, 10:21:01 am
Quote
000000011001001010000100100001000110010010000100100001001001010010000100
000000011001001010000100011001001000010010000100100001001001010010000100
000000011001001010000100100001001000010001100100100001001001010010000100
000000010101010110000100100001001000010010000100100001001001010010000100
It's a beauty >:D ^-^

Indeed  8) SOON more details !!!!!!! I got it running.  8)

I had a though time to find out some fact NOT mentioned in PFS154/PMS154 datasheet:
TM3 and PWGM2 share the same interrupt flag.
This means if you have TM3 and PWMG1 enabled, you will get interrupt requests from BOTH.
COMP and PWMG1 also share one interrupt flag.

Only the PFS154.INC header file reveals this:

Code: [Select]
INTEN IO_RW 0x04
$ 7 @4 : X, TM3 | PWMG2
$ 4 @3 : X, COMP | PWMG1

So my timing calculations been always half/double of what I expected.  |O |O |O |O |O |O |O


With the correct timing calculation I found the bit rate to be 1736 bits/sec  8)


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 06, 2020, 01:27:14 am
I am trying to implement tone function.
I am looking for a way to do microseconds delay (like delayMicroseconds() in Arduino). However, existing delay functions are either for milliseconds only or way too large and use all the SRAM.

Any help would be greatly appriciated!

The delay.h file from the free-pdk-examples repo (https://github.com/free-pdk/free-pdk-examples/blob/master/include/delay.h) has a _delay_us(us) macro in addition to the _delay_ms(ms) macro and only uses up (at most) 7 bytes of SRAM (less if you comment out the delay loop methods that aren't needed).

If you already tried using that delay.h file and are still running out of SRAM, it could be one of the following issues:
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 06, 2020, 01:57:37 am
So, here's my new rapid prototyping adapter and setup:


I am finding this setup much easier/quicker than anything else I have tried to date, including a dedicated 'dev board'.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 06, 2020, 10:20:19 pm
The delay.h file from the free-pdk-examples repo (https://github.com/free-pdk/free-pdk-examples/blob/master/include/delay.h) has a _delay_us(us) macro in addition to the _delay_ms(ms) macro and only uses up (at most) 7 bytes of SRAM (less if you comment out the delay loop methods that aren't needed).

If you already tried using that delay.h file and are still running out of SRAM, it could be one of the following issues:
  • Possibly there is a bug in the version of SDCC you are using?  Try the latest nightly.
  • If you are including delay.h in multiple .c source files, each one seems to get their own allocation of the method parameters for some reason.  The file should really be broken out to separate delay.h and delay.c files to fix this.  I'll update the examples repo at some point.

Thank you for the advice! However, Even I stripped the delay.h to the smallest possible, I still got a SRAM full error.
Here is my source code: https://gist.github.com/Kashouryo/fcf1a8a6995ab7934b9abf936646f6ad
||ASlink-Warning-RAM value 134 too large (128B max)|

Thank you!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 06, 2020, 10:41:43 pm
Thank you for the advice! However, Even I stripped the delay.h to the smallest possible, I still got a SRAM full error.
Here is my source code: https://gist.github.com/Kashouryo/fcf1a8a6995ab7934b9abf936646f6ad
||ASlink-Warning-RAM value 134 too large (128B max)|

Ok, I see the problem now.

The _delay_us(us) macro is meant to be used with constants that are used to calculate the correct number of delay cycles at build time, not variables that would require the calculation at run-time.

So, use this:
Code: [Select]
_delay_us(100);

... instead of this:
Code: [Select]
uint8_t testVal = 100;
_delay_us(testVal);

If you really need something that is more variable at run-time you will have to come up with a different solution.

It looks like you are running at 1MHz, so each cycle is already 1uS.  So, technically you could skip all the 'calculation' and just call the delay loop directly.  But, there is overhead in calling the delay function as well as the delay loop (7 cycles overhead, 3 cycles per loop) that would still have to be taken into account.

For short delays, you don't really need the abstraction that the delay function provides, you could just directly do something like the following (inline assembly), but you still have to take into account the overhead (3 cycles overhead (2+1), 3 cycles per loop).
Code: [Select]
  uint8_t testVal = 32;         // 2 cycles - value = ((100uS -3) /3)
__asm
00001$:                             // 3 cycles per loop
  dzsn   _testVal                  // 1 cycle + 1 cycle for final skip
    goto 00001$                   // 2 cycles
__endasm;
You might be able to put some/most of this in a macro and/or possibly SDCC would already generate optimal loop code by just using a while (--testVal); loop or something similar.

Do you have a more complete example of what you are trying to accomplish?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 07, 2020, 01:45:23 am
Do you have a more complete example of what you are trying to accomplish?
I am trying to implement an Arduino-like tone function that outputs a specific frequently on a pin.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 07, 2020, 01:49:29 am
Do you have a more complete example of what you are trying to accomplish?
I am trying to implement an Arduino-like tone function that outputs a specific frequently on a pin.

For something like that, I would just use PWM.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 08, 2020, 12:21:00 pm
Quote
What's up with your 15V supply? It should be going to pin 8 of the opamp, and yours is apparently 1.69V. Is your dc-dc converter disabled, or faulty?

It's a mess for sure - I'm going to start again and hopefully have better success with MKIII.  :-//

Take care,

OneCircuit


Hi all,

Happy to report that although MKIII was a bust, MKIV is functional and I now have a blinking PFS154. It seems the STM32s I sourced are a bit on the dodgy side.  :(

Thanks everyone for all the advice, support, encouragement and all of the hard work making this crazy project in the first place!

Take care,

OneCircuit
www.onecircuit.blogspot.com (http://www.onecircuit.blogspot.com)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 09, 2020, 08:17:26 pm
I put together an extremely basic but useful(at least to me) GUI frontend for easypdkprog.exe.
https://github.com/Kashouryo/FreePDK-WRITER (https://github.com/Kashouryo/FreePDK-WRITER)
[attach=1]
Also, I made this logo for EasyPDK Programmer. It somewhat resembles the Padauk logo.
(https://raw.githubusercontent.com/Kashouryo/FreePDK-WRITER/master/extras/FreePDK.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 14, 2020, 12:23:31 pm
Hi all,

Trying my MKIV programmer with "easypdkprog probe" and get the following...

PFS154 probe
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

...blinky works...

PFS173 probe
Probing IC... found.
TYPE:FLASH RSP:0x1EA2 VPP=4.50 VDD=2.00
IC is supported: PFS173 ICID:0xEA2

...blinky works...

PMS150C probe
Probing IC... found.
TYPE:FLASH RSP:0xF VPP=4.50 VDD=2.00
Unsupported IC

...no blinky... :-\

But "easypdkprog list" gives...

PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes

...so I've tried multiple chips from two different batches of PMS150C but no luck! Any suggestions?

Take care,

OneCircuit
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 15, 2020, 06:16:22 am
Hi all,

Trying my MKIV programmer with "easypdkprog probe" and get the following...

PFS154 probe
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

...blinky works...

PFS173 probe
Probing IC... found.
TYPE:FLASH RSP:0x1EA2 VPP=4.50 VDD=2.00
IC is supported: PFS173 ICID:0xEA2

...blinky works...

PMS150C probe
Probing IC... found.
TYPE:FLASH RSP:0xF VPP=4.50 VDD=2.00
Unsupported IC

...no blinky... :-\

But "easypdkprog list" gives...

PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes

...so I've tried multiple chips from two different batches of PMS150C but no luck! Any suggestions?

Take care,

OneCircuit

Seems like the software is recognising your PMS150C as a flash micro. Make sure your cli software and your programmer firmware are up to date.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rameshd on August 15, 2020, 08:04:34 am
HI All,

Been following this thread since the beginning. Had bought a few hundred Padauk MCUs even before the programmer/compiler was available.

Thanks to all the folks here who did a fantastic work of creating the Compiler and the Programmer, and made programming the MCUs a reality.

Ordered and built the programmer and successfully programmed the MCU. Had ordered the PCB assembly with just the basic components. Screenshot of my order attached here for anyone to reorder(If any permission issue, will be happy to inform).

Meanwhile here is something interesting. MCUs from Shenzhen Zhien:

hxxp://www.zhienchina.com/product/MCU.html
They seem to be making Padauk MCUs as well. But they have other MCUs with embedded Padauks.
Here is an example:
XDM2102x series, a PMS150C + TP4056 Charger + 1 Amp Motor charger, all in one.

[attach=1]

Thanks again,
Ramesh

[attach=2]

EDIT: Added photo of Assembled PCB





Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: cmfcmf on August 15, 2020, 08:56:58 am
Meanwhile here is something interesting. MCUs from Shenzhen Zhien:

hxxp://www.zhienchina.com/product/MCU.html
They seem to be making Padauk MCUs as well. But they have other MCUs with embedded Padauks.
Here is an example:
XDM2102x series, a PMS150C + TP4056 Charger + 1 Amp Motor charger, all in one.

Great find! I added a section for these chips at https://free-pdk.github.io/chips/#xdmfsss-chips (https://free-pdk.github.io/chips/#xdmfsss-chips).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 15, 2020, 01:36:16 pm
Quote
Seems like the software is recognising your PMS150C as a flash micro. Make sure your cli software and your programmer firmware are up to date.

I have tried three linux flavours and also Windows 10, using both pre-built binaries for easypdfprog and compiled versions - but always the same message for the PMS150C chips. The firmware is the latest from the repository (14th July). Is there other cli software I should be updating?

Is it possible to be a hardware issue? It seems unlikely given the other chips can be recognised and programmed. I'm currently trying to build the firmware from the src (EASYPDKPROG.bin) rather than use the github file (EASYPDKPROG.dfu)

Take care,

OneCircuit
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 17, 2020, 10:27:20 pm
Hi all,

Trying my MKIV programmer with "easypdkprog probe" and get the following...

PFS154 probe
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

...blinky works...

PFS173 probe
Probing IC... found.
TYPE:FLASH RSP:0x1EA2 VPP=4.50 VDD=2.00
IC is supported: PFS173 ICID:0xEA2

...blinky works...

PMS150C probe
Probing IC... found.
TYPE:FLASH RSP:0xF VPP=4.50 VDD=2.00
Unsupported IC

...no blinky... :-\

But "easypdkprog list" gives...

PMS150C  (0xA16): OTP  : 1024 (13 bit), RAM:  64 bytes

...so I've tried multiple chips from two different batches of PMS150C but no luck! Any suggestions?

Take care,

OneCircuit

I just tested it with some PMS150C and it works well for me.

./easypdkprog probe -v
Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Probing IC... found.
TYPE:OTP RSP:0x285A0 VPP=4.50 VDD=2.00
IC is supported: PMS150C / PMS15A ICID:0xA16


Maybe the PROBE command is having trouble with your setup (we might find out later).

How about just specifying the IC name and try a READ:

$ ./easypdkprog -n PMS150C read emptypms150c.hex -v
Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Reading IC (1024 words)...done.


=> Please always use the "-v" option to give verbose output. This will show more details in case something is wrong.


JS


BTW... I just saw that you wrote some time ago that you already had success with PMS150C:
On the plus side - my second SMD version had some small success - it recognised the PMS150C, but not the PFS154 or PFS173. It was unable to program any of them...

PMS150C:
easypdkprog probe
Probing IC... found.
TYPE:OTP RSP:0x285A0 VPP=4.50 VDD=2.00
IC is supported: PMS150C / PMS15A ICID:0xA16

Confused.....
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 18, 2020, 08:39:33 am
Quote
Please always use the "-v" option to give verbose output. This will show more details in case something is wrong.

PMS150C
easypdkprog probe -v

Searching programmer... found: /dev/ttyACM0
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3 Protocol:1.3
Probing IC... found.
TYPE:FLASH RSP:0xF VPP=4.50 VDD=2.00
Unsupported IC

PMS150C
easypdkprog -n PMS150C read emptypms150c.hex -v

Searching programmer... found: /dev/ttyACM0
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3 Protocol:1.3
Reading IC (1024 words)...FPDK_ERROR: command ack failed / wrong icid

Compare with PFS154:
easypdkprog probe -v

Searching programmer... found: /dev/ttyACM0
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3 Protocol:1.3
Probing IC... found.
TYPE:FLASH RSP:0x1AA1 VPP=4.50 VDD=2.00
IC is supported: PFS154 ICID:0xAA1

Quote
BTW... I just saw that you wrote some time ago that you already had success with PMS150C:
Confused.....

That "success" was with an earlier version where I could talk to PMS150C (but not program) and not recognise PFS154/PFS173. In version IV just to be interesting I can recognise and program PFS154/PFS173 but not PMS150C - very strange! I'm going to start on MKV soon and hopefully there will be success across the board. Thank you for your help and suggestions!

Take care,
OneCircuit (http://www.onecircuit.blogspot.com)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on September 02, 2020, 05:24:54 am
I am working on an 8 bit PWM tone project. The current status is WIP but in a useable state.

Tested on PFS154, but should work on PMS150C.

The size of the demo program is around 300 words, so it should be able to fit plenty of notes.

half notes are currently not supported. Manual frequency input is not supported due to the way padauk controls the PWM frequency.

https://github.com/Kashouryo/Padauk-tone
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 04, 2020, 05:08:37 am
Finally got my parts in and soldered up a board, woohoo!

It was tricky, I haven't done SMD soldering in a long time so I ended up needing to borrow the services of the friendly neighborhood reflow oven. A couple close calls with old, bubbly tack flux later and I have an assembled pdk programmer.

The trouble now is, I can't seem to flash the firmware with `dfu-util`. Power seems to be going to the board, as checked at the 1x4 male header, but nothing shows up in `lsusb`. Even with `-vv`, all it tells me is:
DFU suffix version 100
dfu-util: No DFU capable USB device available


Is there something obvious I'm missing or is my best option to start poking SMD bits with my multimeter?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on September 04, 2020, 03:39:54 pm
...
The trouble now is, I can't seem to flash the firmware with `dfu-util`. Power seems to be going to the board, as checked at the 1x4 male header, but nothing shows up in `lsusb`.
...
Is there something obvious I'm missing or is my best option to start poking SMD bits with my multimeter?

Did you remember to press and hold the button while plugging it in to enable bootloader mode?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: itelite on September 04, 2020, 05:18:42 pm
Does anyone have any experience with the official Programming tool?  I finally got one, when i insert the PMS150 8 pin IC (using a small break out board) it says "IC Ready",  but when i hit the program button it says "Find a diff IC.".  I have tried 5 different ICs just to make sure, but the results are all the same. 

I sent an email to their support and hopefully hear back, but just wondering if someone else has had this experience.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 05, 2020, 12:38:41 am
...
The trouble now is, I can't seem to flash the firmware with `dfu-util`. Power seems to be going to the board, as checked at the 1x4 male header, but nothing shows up in `lsusb`.
...
Is there something obvious I'm missing or is my best option to start poking SMD bits with my multimeter?

Did you remember to press and hold the button while plugging it in to enable bootloader mode?

Yup. Tried every boolean combination of Button First | Plugging In | Button While Doing lsusb. No change in the output.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: wolf22 on September 05, 2020, 10:57:39 am
Yup. Tried every boolean combination of Button First | Plugging In | Button While Doing lsusb. No change in the output.

Long time ago I had serious doubts when looking on the schematic of the programmer. The chip would allow programming via SWD and also via bootloader, but instead placing a suitable connector on the board, a pushbutton was placed.

I myself refuse to smudge my HDD by installing such a dfu-util. Programming via bootloader would be the cleanest and easiest way, but the schematic does not provide it. So the best way for you is to use a eval-board from ST and use the onboard ST-Link from this board to program the programmer. A better way would be using a JLink from Segger and manually connect the /reset to it.

And do not forget: fresh chips from ST often need to be bulk erased and unlocked before they are ready to be programmed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 05, 2020, 09:37:41 pm
Yup. Tried every boolean combination of Button First | Plugging In | Button While Doing lsusb. No change in the output.

Long time ago I had serious doubts when looking on the schematic of the programmer. The chip would allow programming via SWD and also via bootloader, but instead placing a suitable connector on the board, a pushbutton was placed.

I myself refuse to smudge my HDD by installing such a dfu-util. Programming via bootloader would be the cleanest and easiest way, but the schematic does not provide it. So the best way for you is to use a eval-board from ST and use the onboard ST-Link from this board to program the programmer. A better way would be using a JLink from Segger and manually connect the /reset to it.

And do not forget: fresh chips from ST often need to be bulk erased and unlocked before they are ready to be programmed.

As luck would have it, I have an STM eval board! It's an STM32F4-Discovery that's currently running MicroPython. I see a port labeled "SWD", and there are some jumpers that seem to allow choosing between "ST-LINK" and "Discovery". Are the right pins exposed on the PDKProg board? I would guess the 4-pin header, but the SWD on my Discovery has 6 pins and I don't know anything about the ST-Link protocol.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 06, 2020, 05:39:13 am

Yup. Tried every boolean combination of Button First | Plugging In | Button While Doing lsusb. No change in the output.

Does your device enumerate when you plug it in while the button is pressed? It should show up as "STM32 BOOTLOADER". If it does not, then there is certainly a hardware issue, like a solder bridge or incomplete connection. Trying to program the device with SWD will not make that issue go away. Choose wisely where you spend your effort :)

Did you check the 3.3V supply? Did you check the USB connection on the PCB?

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 06, 2020, 05:41:03 am
...  Programming via bootloader would be the cleanest and easiest way, but the schematic does not provide it. So the best way for you is to use a eval-board from ST and use the onboard ST-Link from this board to program the programmer. A better way would be using a JLink from Segger and manually connect the /reset to it.

And do not forget: fresh chips from ST often need to be bulk erased and unlocked before they are ready to be programmed.

Sorry, that statement does not even make sense. The STM32F072 comes with integrated USB bootloader that is invoked by the pushbutton. This works very well. No bulk erase or SWD access is needed if it is a fresh device.

There are some people that have trouble soldering the board, but that is unrelated to the bootloader.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on September 06, 2020, 05:52:40 am
I myself refuse to smudge my HDD by installing such a dfu-util.

Why would dfu-util be a smudge ??
That makes no sense

/Bingo

Who uses Tim's Rev 0 programmer wo. any problems  :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on September 06, 2020, 06:00:38 am
I am working on an 8 bit PWM tone project. The current status is WIP but in a useable state.
https://github.com/Kashouryo/Padauk-tone

May i ask why you have included "code" your tone.h file ?
That is a bit unconventional.

/Bingo
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on September 06, 2020, 07:06:53 am
I am working on an 8 bit PWM tone project. The current status is WIP but in a useable state.
https://github.com/Kashouryo/Padauk-tone

May i ask why you have included "code" your tone.h file ?
That is a bit unconventional.

/Bingo

That's actually quite common in padauk projects that I read before.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 06, 2020, 07:28:55 am
I am working on an 8 bit PWM tone project. The current status is WIP but in a useable state.
https://github.com/Kashouryo/Padauk-tone

May i ask why you have included "code" your tone.h file ?
That is a bit unconventional.

/Bingo

That's actually quite common in padauk projects that I read before.

Yeah, but that is not done because this is acceptable style, but because SDCC is not able to remove unused functions from the binary... I know I am also guilty of this, but generally no code should be in the include files.
Title: PFS173 bugs/features
Post by: tim_ on September 06, 2020, 01:35:05 pm
I have been working with the PFS173 again, only to bump into some additional oddities. Not sure where else to document this:

Power on reset

It seems that the PFS173 power on reset does not work if the slew rate is too low. My power supply takes around 50 ms to ramp to final voltage. This will lead to the PFS173 not starting at all. See waveform here:

[attach=1]

When I detach and attach the connection manually, everything is fine:

[attach=2]

11 Bit PWM

It took me quite a while to figure out why the PWM frequency was never the one I tried to set: The 11 Bit PWM is actually a 10 bit counter. The eleventh bit is generated by a ANDing the LSB with the clock. Therefore only 1024 maximum counts should be assumed when calculating the PWM frequency.

There are also several "code options" mentioned in the datasheet. Has anybody already figured out how these can be activated? f.E. seetting the PWM clock source to IHRC*2.
Title: Re: PFS173 bugs/features
Post by: cmfcmf on September 06, 2020, 01:50:02 pm
It seems that the PFS173 power on reset does not work if the slew rate is too low. My power supply takes around 50 ms to ramp to final voltage. This will lead to the PFS173 not starting at all. See waveform here:

I experienced the same behavior. For me, setting the startup speed code option to 'slow' fixed that behavior.

There are also several "code options" mentioned in the datasheet. Has anybody already figured out how these can be activated? f.E. seetting the PWM clock source to IHRC*2.

I haved documented the code options and how to use them here: https://free-pdk.github.io/tutorial#code-options (https://free-pdk.github.io/tutorial#code-options)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bingo600 on September 06, 2020, 05:43:59 pm
Yeah, but that is not done because this is acceptable style, but because SDCC is not able to remove unused functions from the binary... I know I am also guilty of this, but generally no code should be in the include files.

Ahh so it's optimal (codesize) to compile in one large source file ??
That sounds a bit like a linker issue , not being able to skip unused functions.

/Bingo
Title: Re: PFS173 bugs/features
Post by: js_12345678_55AA on September 06, 2020, 05:57:12 pm
I haved documented the code options and how to use them here: https://free-pdk.github.io/tutorial#code-options (https://free-pdk.github.io/tutorial#code-options)

Hi,

the PADAUK IDE code options divide into 2 parts: Real options set in fuse (usually only startup speed, IO drive current and security).
All other code options are "virtual" (you will find this keyword a lot in the PADAUK IDE .INC files) which means they will be written by PADAUK created startup code into other registers.
This means your question "It is unclear whether you are allowed to change these code options while the µC is running, or whether you are supposed to only set them once and leave them as they are." is in fact easy to answer: Yes you can set this values from code whenever you want (PADAUK IDE inserted startup code is doing exactly this).
Also I would not call them "undocumented registers". The PADAUK IDE .INC files do document those registers very well. The virtual option tells you exactly which register and which bits will be setup by the code option you choose in PADAUK IDE.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 06, 2020, 08:30:12 pm

Yup. Tried every boolean combination of Button First | Plugging In | Button While Doing lsusb. No change in the output.

Does your device enumerate when you plug it in while the button is pressed? It should show up as "STM32 BOOTLOADER". If it does not, then there is certainly a hardware issue, like a solder bridge or incomplete connection. Trying to program the device with SWD will not make that issue go away. Choose wisely where you spend your effort :)

Did you check the 3.3V supply? Did you check the USB connection on the PCB?

Ah, yeah, nothing is enumerating with lsusb. I'll start poking with my meter, then. Thanks.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 06, 2020, 10:44:06 pm
 :palm:

I feel like quite the fool now. It turns out that tacky flux like you'd use in a reflow oven is quite the insidious chemical.
All I had to do was replace the button, flux seems to have wormed its way inside and disabled it. A fresh button from the batch passed continuity, the original didn't.

One sudo whack at it later and it's flashed. Next will be getting it to talk to a real chip, it complains there's "nothing found" with more verbosity saying "command ack failed / wrong icid".
I guess it's round two with the multimeter  :D

I wonder if a dunk in isopropyl would clear the button out. Not like I don't have a dozen more on hand, but I might still try it as an investigation of the flux.
I certainly won't be doing the next board the same way!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 07, 2020, 05:45:09 am
:palm:

I feel like quite the fool now. It turns out that tacky flux like you'd use in a reflow oven is quite the insidious chemical.
All I had to do was replace the button, flux seems to have wormed its way inside and disabled it. A fresh button from the batch passed continuity, the original didn't.

One sudo whack at it later and it's flashed. Next will be getting it to talk to a real chip, it complains there's "nothing found" with more verbosity saying "command ack failed / wrong icid".
I guess it's round two with the multimeter  :D

I wonder if a dunk in isopropyl would clear the button out. Not like I don't have a dozen more on hand, but I might still try it as an investigation of the flux.
I certainly won't be doing the next board the same way!

Yeah, after a couple iterations, the typical points of failure become obvious :)

You should compile "easypdkprogtest" and check for the voltages to verify that the programming voltage control works properly.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on September 07, 2020, 07:42:50 am
Hello! Firstly, I want to thank you all for such great work on the Padauk MCUs ecosystem, keep it up  :-+ !

Recently I was interested in using a FreePDK ecosystem because I was not satisfied with the official
software/programmer. Because the original easy-pdk-programmer still needs some components to be purchased and
soldered manually (e.g. USB port, STM32 MCU because it is 0 in stock at jlcpcb), I decided to make easy-to-handsolder
programmer version based on "lite" version schematics by tim_. (But honestly, I just love to solder devices by
myself, so this was the main reasoning behind this :) )

All passives have at least 0805 sizes, and the mini-USB port was used instead of micro-USB,
so it should be relatively easy to solder this programmer by the hand. The only quirky parts
which may be hard to solder are STM32 MCU and MT3608 boost converter.

Although the existing "lite" version of easy-pdk-programmer by tim_
(which was used as a reference for this project) is relatively simple by itself, some additional
simplifications/changes were made:
 
I am still concerned about my routing skills, because I am relatively new to hardware development, so feel free
to correct me if I did something wrong (You can text me here or directly add the issue on the GitHub). The design is not even tested
yet, so it is still work-in-progress but I hope I will be able to polish it on this week and order the PCBs)

Github repo: https://github.com/pacmancoder/easy-pdk-mini

UPD 08.09.2020: Updated project on GitHub:
Added 0.5A 6V PTC fuse, slightly improved routing, changed board dimensions to less bizarre, fixed silkscreen, and drawings layers problems.

UPD 08.09.2020 (2): Update project again:
Small polishing changes before PCB production. Uploaded gerbers, updated images (new revision on the GitHub)

[attach=1]
[attach=2]
[attach=3]
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 09, 2020, 01:34:08 am
:palm:

I feel like quite the fool now. It turns out that tacky flux like you'd use in a reflow oven is quite the insidious chemical.
All I had to do was replace the button, flux seems to have wormed its way inside and disabled it. A fresh button from the batch passed continuity, the original didn't.

One sudo whack at it later and it's flashed. Next will be getting it to talk to a real chip, it complains there's "nothing found" with more verbosity saying "command ack failed / wrong icid".
I guess it's round two with the multimeter  :D

I wonder if a dunk in isopropyl would clear the button out. Not like I don't have a dozen more on hand, but I might still try it as an investigation of the flux.
I certainly won't be doing the next board the same way!

Yeah, after a couple iterations, the typical points of failure become obvious :)

You should compile "easypdkprogtest" and check for the voltages to verify that the programming voltage control works properly.

Hmm... what are the voltages supposed to be? I got 19.83, 5.01, and vref=3.31.

Based on the source for the test, pressing the button should light an LED, but it didn't.
Also, there's a keypress time-out function, but it didn't respond to that either. I had to kill the program with ^C.
Gave it about four runs, same results each time... but now the programmer's just vanished from USB. I guess something failed on the board and took the STM offline.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 09, 2020, 05:13:32 am

Hmm... what are the voltages supposed to be? I got 19.83, 5.01, and vref=3.31.

Based on the source for the test, pressing the button should light an LED, but it didn't.
Also, there's a keypress time-out function, but it didn't respond to that either. I had to kill the program with ^C.
Gave it about four runs, same results each time... but now the programmer's just vanished from USB. I guess something failed on the board and took the STM offline.

Uhm, the voltages should be 5.0 V, 5.0V and 3.3 V. 19.85 certainly is too high, this is even above the nominal boost converter output. Did you miss any resistors anywhere, or are some values are mixed up?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Talrey on September 09, 2020, 11:31:36 pm

Uhm, the voltages should be 5.0 V, 5.0V and 3.3 V. 19.85 certainly is too high, this is even above the nominal boost converter output. Did you miss any resistors anywhere, or are some values are mixed up?

I'll grant that the build process was a bit messy, but I've probed the lines around the 15V and compared them to the schematics. Definitely not missing anything either.
R17 was reading really low (31kOhm to the stated 100kOhm), but I think that's because I'm measuring it in-circuit: 31kOhm matches the equivalent resistance across it due to some other resistors forming a second path through ground.

Actually, I checked the voltage in a few places while it was plugged in... and the 15V is indeed 15V.
No idea why the program was reading 19.8, and I can't verify because it's not responding.

I wonder if the STM itself was causing the higher voltage somehow, and kicked the bucket so it's not interfering any more?  :-BROKE
Title: Re: PFS173 bugs/features
Post by: tim_ on September 13, 2020, 06:21:55 am
I have been working with the PFS173 again, only to bump into some additional oddities. Not sure where else to document this:

Power on reset

It seems that the PFS173 power on reset does not work if the slew rate is too low. My power supply takes around 50 ms to ramp to final voltage. This will lead to the PFS173 not starting at all. See waveform here:

When I detach and attach the connection manually, everything is fine:

11 Bit PWM

It took me quite a while to figure out why the PWM frequency was never the one I tried to set: The 11 Bit PWM is actually a 10 bit counter. The eleventh bit is generated by a ANDing the LSB with the clock. Therefore only 1024 maximum counts should be assumed when calculating the PWM frequency.


Some more findings:

Using port B as input

It seems that the input enable register PBDIER has a default reset state of 0x00, while that datasheet states that it is 0xff. I wonder whether this is actually an errata or maybe the registers are usually set by Mini-C.

GPIO rise an fall times

The rise and fall times of the GPIO used in output mode are suprisingly slow. In the image below you can see the output of the PFS173 (yellow trace), loaded with a WS2812 and a scope probe, and the signal after it was regenerated by a WS2812.

The rise tim of the PF173 is 32 ns, while the fall time is 50ns. The WS2812 (and also other MCUs) have a tr/tf of <5ns into the same load. The tr/tf of the PFS173 is much lower than even the current drive abilities suggest. So this seems to be an intentional design feature. My guess is that helps to protect their on chip supply (a step signal will cause the internal supply to bounce around), without having to introduce additional measures like an internal LDO.

[attach=1]

interrupt latency

I measured interrupt latency to be 6 cycles till the first instruction of the interrupt handler. Can anyone confirm this? Jitter is 2 cycles, assuming an infinite rjmp loop in the main program.



Title: Re: PFS173 bugs/features
Post by: cmfcmf on September 13, 2020, 10:23:49 am
It seems that the input enable register PBDIER has a default reset state of 0x00, while that datasheet states that it is 0xff. I wonder whether this is actually an errata or maybe the registers are usually set by Mini-C.

The latter is true, see also https://free-pdk.github.io/tutorial#registers (https://free-pdk.github.io/tutorial#registers)
Title: Re: PFS173 bugs/features
Post by: tim_ on September 13, 2020, 12:31:08 pm
It seems that the input enable register PBDIER has a default reset state of 0x00, while that datasheet states that it is 0xff. I wonder whether this is actually an errata or maybe the registers are usually set by Mini-C.

The latter is true, see also https://free-pdk.github.io/tutorial#registers (https://free-pdk.github.io/tutorial#registers)

Hm... I cannot imagine that all registers contain random values at reset, because there certainly are some combinations that would cause undesireable behavior.
Maybe only a few registers are off. But that's something that can be easily checked.
Title: Re: PFS173 bugs/features
Post by: cmfcmf on September 13, 2020, 01:31:24 pm
It seems that the input enable register PBDIER has a default reset state of 0x00, while that datasheet states that it is 0xff. I wonder whether this is actually an errata or maybe the registers are usually set by Mini-C.

The latter is true, see also https://free-pdk.github.io/tutorial#registers (https://free-pdk.github.io/tutorial#registers)

Hm... I cannot imagine that all registers contain random values at reset, because there certainly are some combinations that would cause undesireable behavior.
Maybe only a few registers are off. But that's something that can be easily checked.

True - the wording can certainly be improved. When I wrote "undefined", I meant "is initialized to a fixed value that may differ from the datasheet, therefore its better to always set all registers explicitly". Of course, it would be even better to have a definitve list of all µCs and their respective true initial register values.
Title: Re: PFS173 bugs/features
Post by: tim_ on September 13, 2020, 01:41:46 pm

Hm... I cannot imagine that all registers contain random values at reset, because there certainly are some combinations that would cause undesireable behavior.
Maybe only a few registers are off. But that's something that can be easily checked.

True - the wording can certainly be improved. When I wrote "undefined", I meant "is initialized to a fixed value that may differ from the datasheet, therefore its better to always set all registers explicitly". Of course, it would be even better to have a definitve list of all µCs and their respective true initial register values.

I wrote a small program to dump the initial content of the PFS173 I/O area.
It's invoked in  _sdcc_external_startup(void) and first copies all registers to the ram, so apart from the flag register and the stack pointer everything should be unchanged.

It seems that CLKCMD is initialized with 0x9e at reset. All other readable bits appear to be zero.

It appears that accessing unused registers or write only registers often yields the result from the previous access. Possible an issue with a floating internal bus.

I wonder what is going on with 2E and 2F? 2F seems to be unstable and changes values between 0x21 and 0x61.

Code: [Select]
Dumping initial state of I/O area
00: F0 F0 A6 9E 00 08 00 00
08: 00 00 00 00 00 00 00 00
10: 20 00 00 00 00 00 00 00
18: 00 00 00 00 00 00 00 00
20: 40 00 FF E0 E0 E0 E0 E0
28: E0 E0 E0 00 00 E0 60 61
30: 00 00 00 00 00 00 00 00
38: 00 00 00 00 00 00 00 00
40: 00 00 00 00 00 00 00 00
48: 00 00 00 00 00 00 00 00
50: 00 00 00 00 00 00 00 00
58: 00 00 00 00 00 00 00 00
60: 00 00 00 00 00 00 00 00
68: 00 00 00 00 00 00 00 00
70: 00 00 00 00 00 00 00 00
78: 00 00 00 00 00 00 00 00

Edit: It seems that the I/O register data bus will simply hold the previous value when reading from a WO or nonexistant register. When writing a value to one register, the same value will appear when reading from an invalid location.

Using that fact it is possible to identify all write only or nonexistant registers. In the hexdump below, every such register is marked with 0x55.

Code: [Select]
Dumping initial state of I/O area
00: F0 55 A6 9E 00 08 00 55
08: 55 55 55 55 55 55 55 55
10: 20 00 00 00 00 00 00 55
18: 00 00 00 55 55 55 55 55
20: 40 00 FF E0 55 55 55 55
28: 55 55 55 00 55 E0 60 21
30: 00 00 55 55 00 00 55 55
38: 55 55 55 55 55 55 55 55
40: 00 55 55 55 55 55 00 55
48: 55 55 55 55 00 55 55 55
50: 55 55 55 55 55 55 55 55
58: 55 55 55 55 55 55 55 55
60: 55 55 55 54 55 55 55 55
68: 55 55 55 55 55 55 55 55
70: 55 55 55 55 55 55 55 55
78: 55 55 55 55 55 55 55 55

Hm... there seems to be something undocumented at the adresses 0x2d, 0x2e,  0x2f

Hmmm....  0x2d is cleary a control register. Reset state is 0xE0. Bits 7-5,3,1,2 are R/W, Bits 4 and 2 RO. 0x2e and 0x2f appear to be read only.
Any ideas what this could be? It's also not mentioned in the official includes. These could possibly be test registers.
Title: Re: PFS173 bugs/features
Post by: js_12345678_55AA on September 13, 2020, 07:29:34 pm
Hm... there seems to be something undocumented at the adresses 0x2d, 0x2e,  0x2f
Hmmm....  0x2d is cleary a control register. Reset state is 0xE0. Bits 7-5,3,1,2 are R/W, Bits 4 and 2 RO. 0x2e and 0x2f appear to be read only.
Any ideas what could this be? It's also not mentioned in the official includes. These could possibly be test registers.

I think I have an idea what it could be...

Some time ago when I was deep into research I found out about the really undocumented RFC (Resistance to Frequency Converter). This might be used as a poor men's touch interface or ADC?
You can still find some comments only in some of the PDK .INC files.

After digging a bit deeper I found some info in an old Puolop datasheet for PTBO165C : http://www.htsemi.com/xiazai.aspx?aa=/include/upload/download/_20180709113738742.pdf&bb=PTBO165CXXS (http://www.htsemi.com/xiazai.aspx?aa=/include/upload/download/_20180709113738742.pdf&bb=PTBO165CXXS)

Sections 3 and 4:
3. RF Inverters Functions Description
4. RFC (Resistance to Frequency Converter) Functional Description

This small data sheet explains register settings and how to use them. From the PDK .INC files it is also obvious that this feature is present in some more IC (not only in 165C). Maybe it is just not working and that's why missing from data sheet or it is sold as extra feature in different IC marketing derivates.

Have fun,

JS
Title: Re: PFS173 bugs/features
Post by: tim_ on September 13, 2020, 07:41:50 pm
Hm... there seems to be something undocumented at the adresses 0x2d, 0x2e,  0x2f
Hmmm....  0x2d is cleary a control register. Reset state is 0xE0. Bits 7-5,3,1,2 are R/W, Bits 4 and 2 RO. 0x2e and 0x2f appear to be read only.
Any ideas what could this be? It's also not mentioned in the official includes. These could possibly be test registers.

I think I have an idea what it could be...

Some time ago when I was deep into research I found out about the really undocumented RFC (Resistance to Frequency Converter). This might be used as a poor men's touch interface or ADC?
You can still find some comments only in some of the PDK .INC files.

After digging a bit deeper I found some info in an old Puolop datasheet for PTBO165C : http://www.htsemi.com/xiazai.aspx?aa=/include/upload/download/_20180709113738742.pdf&bb=PTBO165CXXS (http://www.htsemi.com/xiazai.aspx?aa=/include/upload/download/_20180709113738742.pdf&bb=PTBO165CXXS)

Sections 3 and 4:
3. RF Inverters Functions Description
4. RFC (Resistance to Frequency Converter) Functional Description

This small data sheet explains register settings and how to use them. From the PDK .INC files it is also obvious that this feature is present in some more IC (not only in 165C). Maybe it is just not working and that's why missing from data sheet or it is sold as extra feature in different IC marketing derivates.

Wow, nice find! That does indeed exactly match the pattern of R/W and RO/WO bits. Will look into this

Edit: The PFC154 actually still has the register descriptions in the .INC file and they exactly match to the locations found for the PFS173. Interestingly there is no mentioning of this functionality in the datasheet.

Code: [Select]
RFCC IO_RW 0x36 (0x2D, -)
$ 7 ~ 5, 0 : PA4, PB4, PA0, PB3, X, PB2, X, PB1,
PA3, PB0, PB7, X, PB6, X, DISABLE : 0xE
$ 4 : X, START : WR_BIT
$ 3 : R_TYPE, C_TYPE // PA4 only for C_TYPE
// ICE Only support R_TYPE
$ 2 : X, Overflow
$ 1 : X, Output // PB5

RFCCRH IO_RO 0x37 (0x2E, -)
RFCCRL IO_RO 0x38 (0x2F, -)

Also note that the linecard still shows the RFC functionality in the footnotes (http://www.padauk.com.tw//upload/SelectionGuide/selection_guide_2019H1__20190227_EN-2.png (http://www.padauk.com.tw//upload/SelectionGuide/selection_guide_2019H1__20190227_EN-2.png)), but there is no device listed.

Seems indeed like this functionality was retroactively removed. Possibly it did not perform well...

EDIT: It actually works! The register mapping of the RFC in the PFS173 is the same as in the PFC154. Essentially this peripheral forms an RC oscillator with an RC pair that is connected to a selectable pin. There is a 16 bit counter to count pulses from the RC oscillator which has to be manually started and stopped. I was able to use this circuit to read out light levels incident on a LED, where the LED is abused as a photodiode.

it should also be possible to use this peripheral for touch sensing or as a plant moisture sensor.

The functionality is a bit limited, because the counter has to be manually started and stopped by software. Also, only one channel at a time can be operated.

What is still lacking, is a description of the schmitt trigger voltages.
Title: Re: PFS173 bugs/features
Post by: js_12345678_55AA on September 13, 2020, 09:40:15 pm
interrupt latency
I measured interrupt latency to be 6 cycles till the first instruction of the interrupt handler. Can anyone confirm this? Jitter is 2 cycles, assuming an infinite rjmp loop in the main program.

Did you use SDCC to define the interrupt ?
* SDCC places a GOTO at ISR vector (+2 cycles)
* SDCC adds automatically 3 instructions to a function marked as "interrupt": "push af / mov a, p / push af" (+3 cycles)

Since we need to assume that PC needs to be saved as well (IC is doing this on it's own) this add another (+1 cycle)

==> 2+3+1 = 6 cycles.

Somewhere back in this thread I gave an example how to trick SDCC not to write a GOTO but define ISR directly at ISR vector. Also by specifying the function "naked" you can do the register saving on your own.

This might bring you an ISR latency of only 1 cycle.



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 14, 2020, 11:21:46 am
Hi,

Your main loop is executing an endless loop with GOTO. This is absolute worst case since for sure interrupt will not execute while one instruction is running.

Since GOTO is using 2 instructions, latency of interrupt will be +2 cycles for this worst case.
I'm sure if you make a dummy loop out of 10 NOPs and 1 GOTO then the average latency will go down by 1 cycle.

Now calculations is:
+2 cycles from GOTO in main loop - absolute worst case (maybe use an endless loop with stopexe. This should reduce it to +1 cycle worst case)
+1 cycle store PC before entering ISR
+2 cycles for the GOTO from SDCC
+3 cycles for storing AF + p
+1 cycle to execute your set1 instruction
====
= 8-9 cycles which is very close to your measurement.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 14, 2020, 01:59:02 pm
It seems that the PFS173 spends two more cycle on something else...

That's interesting and good to know for a cycle accurate emulation :-)

Maybe you can change the main loop to set / reset another output pin so the 2 ghost cycles can be proofed:

$1:
    set1 PB,2
    set0 PB,2
    set1 PB,2
    set0 PB,2
    set1 PB,2
    set0 PB,2
    set1 PB,2
    set0 PB,2
    set1 PB,2
    set0 PB,2
    goto $1

Thanks for your research.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 16, 2020, 08:51:39 pm
FYI, the RFC can also be found in the PFS154. Found in S08 and S16, so I guess it is in all package versions of the PFS154.

It's at addresses 0x36,0x37,0x38, just as indicated in the PFC154 include file.

I/O space dump below. There do not seem to be any other undocumented R/W or RO registers.

0x55 is an unused or WO register, the other value reflect the reset state.

Code: [Select]
Dumping initial state of I/O area
00: F0 55 66 9E 00 87 00 55
08: 55 55 55 55 55 55 55 55
10: 01 00 00 55 00 00 00 55
18: 00 55 54 55 00 00 55 55
20: 00 55 55 55 55 55 00 55
28: 55 55 55 55 00 55 55 55
30: 55 55 00 00 55 55 F4 00
38: 00 55 55 55 55 55 55 55
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on September 23, 2020, 09:40:09 pm
A little update about easy-pdk-mini (https://github.com/pacmancoder/easy-pdk-mini) project (easy-pdk-programmer-lite based programmer variant for handsoldering):
- First revision boards were delivered to me and I assembled a single board using only my soldering iron, so the main idea of my board variant holds well!
- I messed up schematics for opamp wiring when porting EasyEDA schematics to the KiCAD, so to make the first revision boards work, some trace-cutting and wire soldering was required |O.
- But in the end, It works! I am happily flashed PMS150C and PFS173 chips (Bye-bye, horrible Padauk's Mini-C!) :-+

As for the second board revision, I changed the following:
- Fixed opamp wiring. Now everything should work perfect.
- USB-B Through-hole port is used instead of Mini-USB, because Mini-USB soldering without hot air soldering station is, indeed as painful as Micro-USB hand-soldering.

The updated board files can be downloaded from my github repo, if anyone interested.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 26, 2020, 02:41:13 pm
JS, would you please add the STM32 Bin file along the DFU one too,
In a new design I have connected bootpin to ground, I can only program the STM32 with j-link and it would accept bin file or hex file.

Thanks
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 28, 2020, 03:36:43 pm
JS, would you please add the STM32 Bin file along the DFU one too,
In a new design I have connected bootpin to ground, I can only program the STM32 with j-link and it would accept bin file or hex file.

Thanks

Hi,

the .DFU file is same as the .BIN file. It just has a few of extra bytes appended to the end. It does not matter if you use the .DFU file and flash it as .BIN file. The extra bytes at the end will by ignored.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 29, 2020, 10:53:15 am
Thanks JS,
How we can set LVR for PFS173,
Is there any example code?
I want to set it to 4.0V
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 29, 2020, 11:09:05 pm
Thanks JS,
How we can set LVR for PFS173,
Is there any example code?
I want to set it to 4.0V

In case you use the include file from "easypdk/pfs173.h" then setting LVR to 4.0V can be done like this (place it in _sdcc_external_startup() function):

MISCLVR = MISCLVR_4V;

Also make sure that you do NOT set MISC_LVR_DISABLE ins MISC register.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on September 30, 2020, 07:27:56 am
Thanks JS, I have done it, But I have a problem, the MCU some times would not boot after applying voltage to it, I thought maybe adding LVR would solve it, But the problem still remains, Do you have any other  suggestion?

The PFS173 is powered from a DC/DC convertor, (the convertor has a slow startup voltage).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 01, 2020, 06:46:02 pm
Thanks JS, I have done it, But I have a problem, the MCU some times would not boot after applying voltage to it, I thought maybe adding LVR would solve it, But the problem still remains, Do you have any other  suggestion?

The PFS173 is powered from a DC/DC convertor, (the convertor has a slow startup voltage).

Hard to diagnose this without more info. If I remember correctly similar problem was reported from tim? some posts ago.

Some things to try come to my mind:
- try to add a WDRESET instruction as early as possible in your code (I saw this in the standard PADAUK IDE startup code. For some reason they place WDRESET very early)
- disconnect PA.5 for testing (maybe you somehow trigger the programing sequence in case PA.5 gets a small voltage early - e.g. 2.5V on PA.5 and shortly after >4.5V on VDD could cause this).

For further assistance:
- could you create a minimal SDCC C program which has this behavior and share the source
- could you capture the voltage input to VDD pin of the MCU when your DC/DC starts up (oscilloscope trace)?
- could you capture the voltage input to PA.5 pin of the MCU when your DC/DC starts up (oscilloscope trace)?
- could you share the hardware setup / schematic which causes this behavior?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 08:18:13 am
Dear JS
Thanks for your help, Unfortunately I have an analog oscilloscope, So I can not capture the wave form,

But I can share my code

Also This is the schematic, Note that Vin is coming from a secondary isolated winding from a flyback convertor.
(https://img.techpowerup.org/201003/untitled.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 03, 2020, 11:48:07 am
Dear JS
Thanks for your help, Unfortunately I have an analog oscilloscope, So I can not capture the wave form,
But I can share my code
Also This is the schematic, Note that Vin is coming from a secondary isolated winding from a flyback convertor.

I can't see anything wrong here.

But I just got an idea what could be the problem:

In case VDD slowly ramps up, the IC will start execution when VDD >= 1.8V. The IC itself can run with very low voltage BUT the max clock speed can not be 8MHz for SYSCLK then (check datasheet).

As a small test just add a delay right at the start of _sdcc_external_startup()   (before using EASYPDK init sysclock):

unsigned char _sdcc_external_startup(void)
{
  for(uint32 delay=10000;delay>0;delay--); //delay before switching to high clock, use higher / lower numbers to check different delays
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V
  return 0;
}

If this works you also might use ADC or internal COMP to measure VDD and wait before you switch to high sysclock (wait for VDD>=4.0 V)

If it still does not work, you should try to set the FUSE for SLOW IC startup (which I think uses even slower clock... until you reach the point where you setup sysclock yourself):

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_SLOW);
  for(uint32 delay=10000;delay>0;delay--); //delay before switching to high clock, use higher / lower numbers to check different delays
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V
  return 0;
}



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 01:03:58 pm
Thanks JS, But there is a wired error at compile time!

what's going on wrong?
(https://img.techpowerup.org/201003/untitled205.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 01:07:26 pm
I have changed the delay  variable name, Now it would compile, But It can not calibrate the chip!
(https://img.techpowerup.org/201003/untitled173.png)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on October 03, 2020, 01:12:38 pm
Probably calibration is timing out. Put calibrate function call before delay loop
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 03, 2020, 01:19:12 pm
Probably calibration is timing out. Put calibrate function call before delay loop

NO, Please do NOT put calibration function before the delay. The purpose of the delay is to wait before setting up the higher sysclock which is needed to be done before calibration code.

Instead you can use the factory calibration for testing:

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_SLOW);
  for(uint32_t delay=10000;delay>0;delay--); //delay before switching to high clock, use higher / lower numbers to check different delays
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_USE_FACTORY_IHRCR_16MHZ();           //use factory calibration value
  return 0;
}


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on October 03, 2020, 01:20:13 pm
Maybe take a look at application note below. It clearly says that it's for PMC150/PMC153/  PMC156/PMC166 but who knows, maybe its 'bug' 'fixed' in orginal IDE .

http://www.padauk.com.tw//upload/ApplicationNote/PMC-APN006-PMC150_153_156_166_against_rapid_change_in_power_v003_EN_.pdf (http://www.padauk.com.tw//upload/ApplicationNote/PMC-APN006-PMC150_153_156_166_against_rapid_change_in_power_v003_EN_.pdf)

Maybe create some minimal code that changes pin state (something like from above Application note oscilloscope plot) and make some tests.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 03, 2020, 01:25:54 pm
Maybe take a look at application note below. It clearly says that it's for PMC150/PMC153/  PMC156/PMC166 but who knows, maybe its 'bug' 'fixed' in orginal IDE .

http://www.padauk.com.tw//upload/ApplicationNote/PMC-APN006-PMC150_153_156_166_against_rapid_change_in_power_v003_EN_.pdf (http://www.padauk.com.tw//upload/ApplicationNote/PMC-APN006-PMC150_153_156_166_against_rapid_change_in_power_v003_EN_.pdf)

Maybe create some minimal code that changes pin state (something like from AN oscilloscope plot) and make some tests.

Not exactly matching the problem, but the suggestion to set INTRQ to 0 is a good one.

Looks like in case IC (auto) resets some bits of INTRQ might be / get set and in case the interrupt handler does not process (clear all INTRQ bits) interrupt will run for ever (after exit of interrupt, IC sees at least one INTRQ bit is (still) set and interrupt is executed again, ...)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 01:33:48 pm
JS, The new changes would not do any calibration!

(https://img.techpowerup.org/201003/untitled167.png)

Can you confirm that the UART TX  can be put on PA6 pin, I'm using PFS173 8pin version

Regards
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 01:34:58 pm
Quote
Not exactly matching the problem, but the suggestion to set INTRQ to 0 is a good one.

Looks like in case IC (auto) resets some bits of INTRQ might be / get set and in case the interrupt handler does not process (clear all INTRQ bits) interrupt will run for ever (after exit of interrupt, IC sees at least one INTRQ bit is (still) set and interrupt is executed again, ..
Where the INTRQ  should be 0?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 01:49:56 pm
JS, I'm testing in Breadboard, when I add anything more than these lines to _sdcc_external_startup, it would not boot
(https://img.techpowerup.org/201003/20201003-171609.jpg)

Code: [Select]
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V

But If I comment out the
Code: [Select]
  //EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_SLOW);
  //for(int cnt=0;cnt<10000;cnt++);

It would work normally in breadboard!


The UART TX signal on PA6 when I have only  these codes in the startup

Code: [Select]
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V

(https://img.techpowerup.org/201003/20201003-171620.jpg)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 03, 2020, 01:59:41 pm
JS, The new changes would not do any calibration!
This is correct. It uses FACTORY CALIBRATION VALUE so the programmer does not need to do calibration. This was what I wanted to do. Now you can put the delay inside and program the IC without problems.

==> Please test the IC with this setup. It should work perfectly.

======> Maybe the value in delay loop is much to high and you simply do not wait enough (remember IC startup speed is on ILRC which is some kHz instead of MHz!)

Can you confirm that the UART TX  can be put on PA6 pin, I'm using PFS173 8pin version
Regards

Sure, you can use any pin as output for serial TX (except PA.5 which is not a PUSH-PULL type, would need to add a pull up resistor for PA.5 as output).


Where the INTRQ  should be 0?

Just put a INTRQ = 0; anywhere in your code, just BEFORE you call __engint();  to enable interrupts.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 02:14:26 pm
JS, The old code would not do calibration either! it was doing it before
(https://img.techpowerup.org/201003/untitled377.png)

I have done one time this code
Code: [Select]
EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_SLOW);Now I just have commented out
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 03, 2020, 02:33:57 pm
JS, I have found something new On my PCB board, when I flash the Chip, I think it maybe be reset after a short time,

Here is a wave capture of PA6 which is used as UART TXD @ 9600 baud,
Note the output would reset 1.77ms pulses!

(https://img.techpowerup.org/201003/20201003-180005.jpg)

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 03, 2020, 06:05:04 pm
JS, The old code would not do calibration either! it was doing it before
I have done one time this code
Code: [Select]
EASY_PDK_FUSE(FUSE_SECURITY_OFF|FUSE_BOOTUP_SLOW);Now I just have commented out

Not sure what you reference with old code and new code.
Your screenshot shows, that you do a DELAY and CALIBRATION => This can not work.

Please add the startup delay and use factory tuning (no calibration will be done by programmer):

unsigned char _sdcc_external_startup(void)
{
  for(uint32_t delay=10000;delay>0;delay--); //delay before switching to high clock, use higher / lower numbers to check different delays
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_USE_FACTORY_IHRCR_16MHZ();           //use factory calibration value
  return 0;
}


That should be your complete _sdcc_external_startup code. Do not add or remove anything. Just use this code. The only thing you should try is to change the value for delay (10000 or 1000 or 100 or ...) in order to shorten / increase your startup delay. In any case it should work exact like before you started changing the code, but I expect it performs better (no lockups when used with your DCDC) when you found the correct startup delay.

After thinking a bit more about the problem adding the LVR *before* the switch to higher clock rate also might solve the problem. I'm just not sure how long it takes for the new LVR to be effective (maybe a small delay after setting LVR is needed):

unsigned char _sdcc_external_startup(void)
{
  MISCLVR = MISCLVR_4V5;
  for(uint8_t delay=10;delay>0;delay--);        //small delay after setting LVR - before switching to high clock (maybe not needed)

  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V
  return 0;
}



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 04, 2020, 07:14:08 am
Thanks JS,
The Code does not make any calibration, No matter what I put in startup code, I have done all the possible combinations!
(https://img.techpowerup.org/201004/untitled.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2020, 12:21:50 pm
Thanks JS,
The Code does not make any calibration, No matter what I put in startup code, I have done all the possible combinations!

That's very strange, let's investigate.

First check: Please check that you use latest "pfs173.h"
You can verify when you look in pfs173.h and find the following lines:
//set calibration macros
#define EASY_PDK_CALIBRATE_IHRC(frequency,millivolt) EASY_PDK_CALIBRATE_RC_M( EASY_PDK_CALTYPE_IHRC, 0x0B, frequency, millivolt )


Next check: Do you use the latest version of easypdk prog?
You can check by adding the -v option to easypdkprog command line:
easypdkprog -v --icname=PFS173 write build/lvrstartup.ihx
Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Erasing IC... done.
Blank check IC... done.
Writing IC (1592 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 5.00V ... calibration result: 8021146Hz (0x80)  done.


I also found a mistake in the _sdcc_external_startup code.
* MISCLVR is set to trigger <= 4.5V
* calibration is done at 4000 mV = 4.0 V
==> this means calibration can not be done (should give an ERROR)

==> change calibration voltage to your target system voltage of 5V:


unsigned char _sdcc_external_startup(void)
{
  MISCLVR = MISCLVR_4V;

  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,5000);        //tune SYSCLK to 8MHz @ 5.000V
  EASY_PDK_USE_FACTORY_BGTR();                  //use factory BandGap tuning value (tuned @ 5.0V)
  return 0;                                     //perform normal initialization
}


I also made some experiments:

- when setting SYSCLOCK to 8MHz you need to have >=4.0V
- when you power the system with external power supply and slowly increase voltage from 0V to 5V  the IC *WILL HANG* (that's why the LVR should be added)
- adding the LVR setup just in front of the EASY_PDK_INIT_SYSCLOCK is enough to get a stable startup even when you slowly increase voltage from 0V to >=4.0V

unsigned char _sdcc_external_startup(void) {
  MISCLVR = MISCLVR_4V;                                                         //set minimum voltage for 8MHz sysclock (lower voltage will reset IC)
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                                                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,5000);                                        //tune SYSCLK to 8MHz @ 5.000V
  return 0;                                                                     //perform normal initialization
}

Now I'm thinking if we should add setting LVR to the INIT_SYSCLOCK macro...



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on October 04, 2020, 06:40:29 pm
Hello! I am having problems with reading 16-bit timer value using an open-source toolchain:
- When trying to read the T16C value directly in the code, I am receiving the "Unimplemented __sfr16 load" from SDCC.
- I tried to use line of ASM code "__asm__("ldt16 _clocksSpent");" (where clocksSpent is my global uint16_t variable name). This compiles for pdk13 (PMS150C), but when compiling for pdk15 (PFS173) I am getting the following linker error:
Code: [Select]
[build] ?ASlink-Warning-Invalid address for instruction
[build]          file              module            area              offset
[build]   Refby  CMakeFiles\spl    loop              CODE                   000050
[build]   Defin  CMakeFiles\spl    loop              DATA                   010000
[build]
I suspect that clocksSpent may be not word-aligned as LDT16 instruction requires and I just accidentally was being lucky when code successfully compiled for pdk13?
Does anyone have similar error? Is there are any workaround for this?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 04, 2020, 10:23:54 pm
Hello! I am having problems with reading 16-bit timer value using an open-source toolchain:
- When trying to read the T16C value directly in the code, I am receiving the "Unimplemented __sfr16 load" from SDCC.
- I tried to use line of ASM code "__asm__("ldt16 _clocksSpent");" (where clocksSpent is my global uint16_t variable name). This compiles for pdk13 (PMS150C), but when compiling for pdk15 (PFS173) I am getting the following linker error:
Code: [Select]
[build] ?ASlink-Warning-Invalid address for instruction
[build]          file              module            area              offset
[build]   Refby  CMakeFiles\spl    loop              CODE                   000050
[build]   Defin  CMakeFiles\spl    loop              DATA                   010000
[build]
I suspect that clocksSpent may be not word-aligned as LDT16 instruction requires and I just accidentally was being lucky when code successfully compiled for pdk13?
Does anyone have similar error? Is there are any workaround for this?

Looks like "__sfr16 load" is not implemented by SDCC (PDK13/PDK14/PDK15 are all affected).
Need to file a bug report to SDCC compiler project: https://sourceforge.net/p/sdcc/bugs/

Workaround:
Your __asm code as replacement is correct and compiles for all processors. But like you already found out it is required to have a WORD aligned variable.

* you can either word align the variable (place all your word variables (uint16_t) at the top of your source file (as global variables)

* or you use the compiler virtual "p" register in your assembly (the "p" register is just a reserved word at memory position 0/1, designed exactly for this kind of purpose - always have at least one word aligned variable):

  uint16_t clocksSpent;
  ...
  __asm__("ldt16 p               \n"
          "mov a, p              \n"
          "mov _clocksSpent, a   \n"
          "mov a, p+1            \n"
          "mov _clocksSpent+1, a \n");


I expect that the sfr16 load implementation will produce same assembly as above when added to SDCC

JS


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on October 05, 2020, 07:14:05 am
Thanks, JS!
Yes, moving around variable declarations helps, works great as a temporary solution!

The second way (with virtual p register) seems more reliable, though. The only concern I have here is that I may accidentally clobber the previous (potentially important) p,a,f register values when running inline assembly? I suppose, additional push af / pop af and push/pop of with p register value may be required? Or p/a/f registers can be overwritten by the inline assembly without any consequences?
Code: [Select]
; save context
push af
mov a, p
push af
mov a, p + 1
push af
; load TM16C
ldt16 p
mov a, p
mov _clocksSpent, a
mov a, p+1
mov _clocksSpent+1
; restore context
pop af
mov p + 1, a
pop af
mov p, a
pop af
However, if additional context saving is required, 13 cycles to load the word feels pretty slow in comparison to single ldt16 instruction. Maybe in the end, it is better to just move variable declarations around  :-\
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 05, 2020, 08:03:21 am
Thanks, JS!
Yes, moving around variable declarations helps, works great as a temporary solution!

The second way (with virtual p register) seems more reliable, though. The only concern I have here is that I may accidentally clobber the previous (potentially important) p,a,f register values when running inline assembly? I suppose, additional push af / pop af and push/pop of with p register value may be required? Or p/a/f registers can be overwritten by the inline assembly without any consequences?
Code: [Select]
; save context
push af
mov a, p
push af
mov a, p + 1
push af
; load TM16C
ldt16 p
mov a, p
mov _clocksSpent, a
mov a, p+1
mov _clocksSpent+1
; restore context
pop af
mov p + 1, a
pop af
mov p, a
pop af
However, if additional context saving is required, 13 cycles to load the word feels pretty slow in comparison to single ldt16 instruction. Maybe in the end, it is better to just move variable declarations around  :-\

As soon as you use a __asm statement the compiler treats the values of a, f and p as "dirty" so no extra context saving required.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 05, 2020, 09:49:49 am
Quote
First check: Please check that you use latest "pfs173.h"
You can verify when you look in pfs173.h and find the following lines:
//set calibration macros
#define EASY_PDK_CALIBRATE_IHRC(frequency,millivolt) EASY_PDK_CALIBRATE_RC_M( EASY_PDK_CALTYPE_IHRC, 0x0B, frequency, millivolt )
The file is the latest version


Quote
Next check: Do you use the latest version of easypdk prog?
You can check by adding the -v option to easypdkprog command line:
easypdkprog -v --icname=PFS173 write build/lvrstartup.ihx
Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Erasing IC... done.
Blank check IC... done.
Writing IC (1592 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 5.00V ... calibration result: 8021146Hz (0x80)  done.

This is the output, it looks it's older, I will update and let you know the results
(https://img.techpowerup.org/201005/untitled.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on October 05, 2020, 10:05:05 am
JS,The problem is solved, the files version was old, But I think you should put the MISCLVR = MISCLVR_4V; in startup for stable operation.
Big Thumbs up :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 05, 2020, 08:21:34 pm
Oh wow, nice find, JS! So instead of spending much time with a complicated power-on-reset they implemented it in software. You got to admire the ingenuity of the paudauk designer, but that was quite a trap.

Now the PFS173 also works with my power supply, I verified in the scope picture below. Channel2 is connected to PB0, which will output a single pulse at the beginning of the program before setting of LVS and oscillator.
The CPU starts executing at VCC=2V (ch1) and keeps resetting until 4V is reached. Then it does indeed execute at 8 MHz in a stable way.

We should somehow introduce this as a standard include because it is a very annoying pitfall.

Code: [Select]
unsigned char _sdcc_external_startup(void)
{
PBC=BIT0;
PB=BIT0;
PB=0;
MISCLVR = MISCLVR_4V;

CLKMD = CLKMD_IHRC_DIV2 | CLKMD_ENABLE_IHRC;  // 16/2=8 Mhz main clock
EASY_PDK_CALIBRATE_IHRC(F_CPU, 5000); // tune SYSCLK to 9.6MHz @ 5.00V
return 0; // perform normal initialization
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on October 05, 2020, 08:33:50 pm
Oh wow, nice find, JS!

Yes, agreed... nice find JS!  And thanks for the visualization tim_!

This probably explains some weirdness I was also seeing where things weren't always starting properly when I was using a bench PSU.  I kept thinking I had a bug somewhere in my code, although it always seemed to work if I manually disconnected and re-connected power instead of just using the PSU's on/off button.  I'll have to dig that project back out and see if this code change fixes it.

The CPU starts executing at VCC=2V (ch1) and keeps resetting until 4V is reached. Then it does indeed execute at 8 MHz in a stable way.

According to the datasheets I just checked, we should be able to achieve 8 MHz down to 3.5V.  Can you verify things are still stable with a lower LVR?

We should somehow introduce this as a standard include because it is a very annoying pitfall.

I'll add it to the appropriate free-pdk-examples later today.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 05, 2020, 08:53:02 pm
According to the datasheets I just checked, we should be able to achieve 8 MHz down to 3.5V.  Can you verify things are still stable with a lower LVR?

The PFS173 I have been using for testing worked down to 2.35V at 8MHz. I suppose that should not be taken for granted as it will change with higher temperature and device to device variation.
I guess 3.5V is safe.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on October 05, 2020, 09:01:55 pm
According to the datasheets I just checked, we should be able to achieve 8 MHz down to 3.5V.  Can you verify things are still stable with a lower LVR?

The PFS173 I have been using for testing worked down to 2.35V at 8MHz. I suppose that should not be taken for granted as it will change with higher temperature and device to device variation.
I guess 3.5V is safe.

Here is what I found so far (by parsing the datasheets):

Code: [Select]
DEVICE:           PFS154         PFS172  PFS173  PMS150C PMS152  PMS154C PMS171B
MISCLVR or FUSE:  MISCLVR(basic) MISCLVR MISCLVR FUSE    MISCLVR FUSE    MISCLVR
>= 8 MHz needs >= 3.5V           3V      3.5V    3V      3.5V    3.5V    3V
>= 4 MHz needs >= 2.5V           2.2V    2.5V    2.2V    2.5V    2.5V    2.2V
>= 2 MHz needs >= 2V             1.8V    2.2V    2V      1.8V    1.8V    1.8V

Unfortunately, I'm not sure there is enough similarity between devices to make a standard include for this.  I was thinking of something similar to the AUTO_INIT_SYSCLOCK() macros from free-pdk-examples/include/auto_sysclock.h.  It looks like 3.5V would work across the board for all devices even though some only seem to need 3V.  But the bigger problem is that the MISCLVL register is also used for other things, and sometimes LVR needs to be set by a FUSE instead of the MISCLVR register.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 05, 2020, 09:03:05 pm
Interesting, it seems now also the undocumented clk setting can be used to activate 16 MHz in the PFS173:

Code: [Select]
unsigned char _sdcc_external_startup(void)
{
MISCLVR = MISCLVR_4V;

CLKMD = CLKMD_IHRC | CLKMD_ENABLE_IHRC;  // 16 Mhz main clock
PDK_USE_FACTORY_IHRCR_16MHZ();

return 0; // perform normal initialization
}

My 8 MHz blinky is twice as fast, so it seems to work. I never tried it before, maybe it worked all along?

Edit: Minimum voltage for 16 MHz is 3.9V. So I suppose that it is quite marginal and even 5V might fail at higher temperatures. I guess that is why they did not document this setting.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on October 05, 2020, 10:17:09 pm
Looks like my concerns about using p registers were right.
I have tried to perform ldt16/stt16 with the p register in __asm__ block, but my program started to work abnormally. After further investigation, I found out that sdcc ignores fact that p virtual register is overriten by the custom asm code. For example, I have the following fucntion (this example with stt16, it is broken the same way ldt16 do):
Code: [Select]
#define __stt16(var) __asm__("mov a, "_STR_VAR(var)"\n"\
    "mov p, a\n"\
    "mov a, "_STR_VAR(var)"+1\n"\
    "mov p+1, a\n"\
    "stt16 p\n");
// ....
static uint16_t tm16Value = 0;

void reset_timer16_counter(void) {
    uint8_t timerMode = T16M;
    T16M = T16M_CLK_DISABLE;
    __stt16(tm16Value);
    T16M = timerMode;
}

The asm code generated for this function is the following:
Code: [Select]
0x004c:   0x0186    MOV A, IO(0x06)  ;T16M
0x004d:   0x1700    MOV [0x00], A     ; <---- sdcc uses p as local variable storage
0x004e:   0x5700    MOV A, 0x00
0x004f:   0x0106    MOV IO(0x06), A  ;T16M
0x0050:   0x1f02    MOV A, [0x02]
0x0051:   0x1700    MOV [0x00], A     ; <---- value overwritten by the __asm__ block
0x0052:   0x1f03    MOV A, [0x03]
0x0053:   0x1701    MOV [0x01], A
0x0054:   0x0600    STT16 [0x00]
0x0055:   0x1f00    MOV A, [0x00]      ; <---- restored wrong value
0x0056:   0x0106    MOV IO(0x06), A  ;T16M
0x0057:   0x007a    RET

If I add additional context saving for __asm__ block, everything is working normally.

So for now, the most usable way of using ldt16/stt16 is to make sdcc to place uint16_t variables to the word aligned address by placing as the first items in the first translation unit as JS suggested, or by introducing the additional single byte variables before ldt16/stt16 operand variables if their address is non-aligned.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on October 06, 2020, 01:38:18 am
I just finished up and published another Padauk related project... a temperature controlled 4-pin PWM fan controller: https://github.com/serisman/pdk-temp-pwm-fan/

I needed this for a UPS that was converted to run on a much larger battery, and therefore have a much longer run-time.  The problem with longer run-time is that the original design assumed it wouldn't be running for long enough to worry about heat dissipation, so adding a fan was a must.  Since it will be in bypass mode 99.99% of the time, I didn't want to run the fan at a full 100% all the time (waste of power and noisy).

So, this circuit and firmware were whipped up to be able to run the fan at a minimum setting until cooling capacity is actually needed.

Temperature measurement is performed by using a 10k NTC thermistor between 5V VCC and a 1K resistor to GND.  The output of this voltage divider is connected to the COMP+ pin, and the COMP- pin is connected to the internal voltage source that can be set between GND and 1/2 VCC in 16 steps.  So... not the most precise temperature measurement, but works fine on the '3 cent' 6-pin PMS150C, and good enough for the crude temperature control I needed!

Originally, I had attempted to build this to control a 3-pin (non-PWM) fan, but wasn't happy with the performance so I switched to the 4-pin PWM fan which is much easier to control and has much better performance (i.e. it can go to slower speeds, lower noise, more efficient).  The fan I wanted to use was a 4-pin anyway, so no real loss.  I may re-approach the 3-pin design at a future time, because I could see it being handy as well.

As usual, PCB design and gerber files are available on the GitHub project page.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 06, 2020, 06:08:43 am
Interesting, it seems now also the undocumented clk setting can be used to activate 16 MHz in the PFS173:

[…]

My 8 MHz blinky is twice as fast, so it seems to work. I never tried it before, maybe it worked all along?

Edit: Minimum voltage for 16 MHz is 3.9V. So I suppose that it is quite marginal and even 5V might fail at higher temperatures. I guess that is why they did not document this setting.

Historically, many datasheets mentioned a 16 MHz setting, but by now, it apparently has been removedf rom all (and any time I asked Padauk about contradictionary information regarding it in diffeerent sections of a datasheet, the resolution was removal of the 16 MHz setting). I suspect that it didn't work reliably in some way.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 06, 2020, 06:25:27 am
Thanks JS, But there is a wired error at compile time!

what's going on wrong?

To use uint32_t, you need to
Code: [Select]
#include <stdint.h>
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 08, 2020, 04:57:57 pm
Hi,

I added automatic LVR setup for high clock rates to the Examples folder of the easy-pdk-programmer-software *development branch*.

=> https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src  and defines in "easypdk" folder there.

Now when you use EASY_PDK_INIT_SYSCLOCK_8MHZ() it will automatically set the correct LVR value for the IC (either via MISCLVR register or via FUSE).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 08, 2020, 05:48:03 pm
I added automatic LVR setup for high clock rates to the Examples folder of the easy-pdk-programmer-software *development branch*.

=> https://github.com/free-pdk/easy-pdk-programmer-software/tree/development/Examples/src  and defines in "easypdk" folder there.

Nice! I noticed you also added 16 MHz at 4 Volt for the PFS154 and at 4.5V for the PFS173. Does it mean that the PFS154 is more stable at 16V than the PFS173?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 09, 2020, 11:36:54 am
Nice! I noticed you also added 16 MHz at 4 Volt for the PFS154 and at 4.5V for the PFS173. Does it mean that the PFS154 is more stable at 16V than the PFS173?

It does not mean anything. 4V was just the highest value available for PFS154 and I just used the highest possible LVR value for 16MHz... most likely it will not work reliable. Time / experiments will tell.

JS.

EDIT: I did some overclocking speed tests (not sure how stable this is, just the calibration loop).

Hi-Scores:

PFS173: VDD=5.7V, SYSCLOCK=16MHZ, CALIBRATED to 24MHZ  ;D (the higher VDD seems to make a huge difference, @5.0V max was 18Mhz):

...
  EASY_PDK_INIT_SYSCLOCK_16MHZ();                //use 16MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(24000000,5700);        //tune SYSCLK to 24MHz @ 5.700V
...


Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Erasing IC... done.
Blank check IC... done.
Writing IC (186 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=24000000Hz @ 5.70V ... calibration result: 24199035Hz (0x9F)  done.


----------------

PFS154: VDD=5.9V, SYSCLOCK=16MHZ, CALIBRATED TO 23MHZ ;D

...
  EASY_PDK_INIT_SYSCLOCK_16MHZ();                //use 16MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(23000000,5900);        //tune SYSCLK to 23MHz @ 5.900V
...


Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Erasing IC... done.
Blank check IC... done.
Writing IC (186 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=23000000Hz @ 5.90V ... calibration result: 23088037Hz (0x9E)  done.



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 13, 2020, 05:46:58 am
PFS173: VDD=5.7V, SYSCLOCK=16MHZ, CALIBRATED to 24MHZ  ;D (the higher VDD seems to make a huge difference, @5.0V max was 18Mhz):

PFS154: VDD=5.9V, SYSCLOCK=16MHZ, CALIBRATED TO 23MHZ ;D

Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.3
Erasing IC... done.
Blank check IC... done.
Writing IC (186 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=23000000Hz @ 5.90V ... calibration result: 23088037Hz (0x9E)  done.


Nice! Looks like the oscillator can be trimmed to run at even higher frequency. Time to bring out the LN2 cooling for serious overclocking :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 07, 2020, 07:38:09 am
No activity here for quite some time?  Some updates that I am aware of:

* There are two nice new projects with the PFS154 by Ralph S. on µC.net:

https://www.mikrocontroller.net/topic/505698 (https://www.mikrocontroller.net/topic/505698)
https://www.mikrocontroller.net/topic/506253 (https://www.mikrocontroller.net/topic/506253)

(Sorry, it's in german)

* Documentation of undocumented features in the Padauk MCUs:

https://free-pdk.github.io/undocumented-features (https://free-pdk.github.io/undocumented-features)

* The design files of the lite-version of the EasyPDKProgrammer are now here:

https://github.com/free-pdk/easy-pdk-programmer-lite-hardware (https://github.com/free-pdk/easy-pdk-programmer-lite-hardware)

The documentation is still in progress, but the design works as is.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 07, 2020, 07:48:20 am
Also, philipp brought up that a few new devices were announced:

https://github.com/free-pdk/easy-pdk-programmer-software/issues (https://github.com/free-pdk/easy-pdk-programmer-software/issues)

The PFS252 is the most interesting of the bunch

http://www.padauk.com.tw/en/news/show.aspx?num=219 (http://www.padauk.com.tw/en/news/show.aspx?num=219)

It seems to be the first low cost device with two FPPAs.

Unfortunately LCSC seems to be very reluctant to pick up new devices from Padauk for their lineup, I asked them to no avail.
It's still not easy to obtain even the "older" new devices like PFS172.



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on November 07, 2020, 08:00:34 am
Please try to add more industrial grade parts to the supported list, Parts with -40 to 85C working temp
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 17, 2020, 09:01:00 pm
Sooo, in case someone is looking for a new 8 bit MCU to reverse. There seems to be a a new chinese competitor to Padauks strategy, aptly named "Fremont Micro Devices". Of course, they are absolutely not based in Fremont. (Correction, they seem to have an office there, but it's not even listed on their homepage)

https://lcsc.com/products/Other-Processors-And-Microcontrollers-MCUs_11116.html?q=fremont%20micro%20devices (https://lcsc.com/products/Other-Processors-And-Microcontrollers-MCUs_11116.html?q=fremont%20micro%20devices)
https://www.fremontmicro.com/en/product/mcu/index.aspx (https://www.fremontmicro.com/en/product/mcu/index.aspx)

They have a line up of flash based 8 bit microcontrollers. The cheapest one (FT60F210) is only $0.05, beating the PFS154. The documentation is a bit unclear whether they are really flash based, but there are several references. They don't look too exciting. The core is again PIC-related. One interesting feature is integrated EEPROM. They also have slightly more complex periphery than Padauk in the larger devices.

The programming interface seems to be low voltage, which is interesting. A big caveat is that the documentation only seems to be chines.

Well, it's not too interesting, as there are already Padauk MCUs.

edit: Okay, the MCU core is a PIC16 clone. The IDE actually comes with an ancient version of the Hi-tech C-compiler.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on November 25, 2020, 06:10:02 pm
Their FT16F01x series is basically PIC16F648. They might even binary compatible with eachother.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pastaclub on December 01, 2020, 11:33:26 am
Hi, I'm trying to find out what I need to know about the pins of Padauk's OTP device if they are to be programmed AFTER PCB assembly, not before. The datasheet doesn't say that.

Obviously there are two aspects to it:
- the programming signals must not damage other components connected to the Padauk
- the other components must not interfere with the programming of the Padauk

This should be a non-issue for pins where for example push buttons are connected. But what about pins for example connected to the middle pin of a 5KOhms potentiometer between GND and VCC? Also, is VCC during programming something usual such as 3V3 or can it be way up which risks damaging other components?

I can imagine it could also be an option to have jumpers on the PCB which are manually closed after programming, but I would really need the information of which pins are concerned and what I need to know about them. Can you point me to that information?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 02, 2020, 03:00:56 pm
Hi, I'm trying to find out what I need to know about the pins of Padauk's OTP device if they are to be programmed AFTER PCB assembly, not before. The datasheet doesn't say that.

Obviously there are two aspects to it:
- the programming signals must not damage other components connected to the Padauk
- the other components must not interfere with the programming of the Padauk

This should be a non-issue for pins where for example push buttons are connected. But what about pins for example connected to the middle pin of a 5KOhms potentiometer between GND and VCC? Also, is VCC during programming something usual such as 3V3 or can it be way up which risks damaging other components?

I can imagine it could also be an option to have jumpers on the PCB which are manually closed after programming, but I would really need the information of which pins are concerned and what I need to know about them. Can you point me to that information?

Hi,

From my experience interfering in any way with any of the programing signals always causes trouble during programing or in the tuning step.

VCC can be as high as 5.8V during programing (depending on IC, have a look at "fpdkicdata.c" in the programmer repository to find "vdd_write_hv" - which is usually the highest vdd during programing)

Suggestion: Even for production runs try to use FLASH parts (e.g. PFS173 is available in almost all packages - even 6 pin version - and does not cost a lot more than OTP variants, if you do not need the ADC and/or the "big" RAM then you also can use PFS154).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rameshd on December 06, 2020, 07:02:45 pm
Here is a placement diagram for the original PDK programmer, which I had created a while back.
Hope it is still useful.

Ramesh
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 09, 2020, 02:27:06 pm
Sooo, in case someone is looking for a new 8 bit MCU to reverse. There seems to be a a new chinese competitor to Padauks strategy, aptly named "Fremont Micro Devices". Of course, they are absolutely not based in Fremont. (Correction, they seem to have an office there, but it's not even listed on their homepage)

https://lcsc.com/products/Other-Processors-And-Microcontrollers-MCUs_11116.html?q=fremont%20micro%20devices (https://lcsc.com/products/Other-Processors-And-Microcontrollers-MCUs_11116.html?q=fremont%20micro%20devices)
https://www.fremontmicro.com/en/product/mcu/index.aspx (https://www.fremontmicro.com/en/product/mcu/index.aspx)

They have a line up of flash based 8 bit microcontrollers. The cheapest one (FT60F210) is only $0.05, beating the PFS154. The documentation is a bit unclear whether they are really flash based, but there are several references. They don't look too exciting. The core is again PIC-related. One interesting feature is integrated EEPROM. They also have slightly more complex periphery than Padauk in the larger devices.

The programming interface seems to be low voltage, which is interesting. A big caveat is that the documentation only seems to be chines.

Well, it's not too interesting, as there are already Padauk MCUs.

edit: Okay, the MCU core is a PIC16 clone. The IDE actually comes with an ancient version of the Hi-tech C-compiler.


I got my hands on 50x FT60F211 thinking they would be compatible enough to be not only used with PIC development tools, but also being programmed with a PIC programmer, which would make them a much much easier to use alternative to Padauk. Sadly, when trying to read them as any kind of 8 pin PIC, my TL866CS complains that it's got an overcurrent issue. Oh well.

Maybe it would be interesting if there's more people willing to help to create a post for reverse engineering these too?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on December 12, 2020, 05:35:52 pm
Since I was interested, instead of hijacking this thread I've created a new one with all the information I've gathered so far: https://www.eevblog.com/forum/projects/fremont-micro-devices-microcontroller-programming/ (https://www.eevblog.com/forum/projects/fremont-micro-devices-microcontroller-programming/)

Help is welcome!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: ali_asadzadeh on December 14, 2020, 02:39:37 pm
Do we have a Verilog implementation of the CPU so it can be used in a FPGA and SDCC can be used for it >:D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on December 20, 2020, 09:47:31 pm
Since I was interested, instead of hijacking this thread I've created a new one with all the information I've gathered so far: https://www.eevblog.com/forum/projects/fremont-micro-devices-microcontroller-programming/ (https://www.eevblog.com/forum/projects/fremont-micro-devices-microcontroller-programming/)

Help is welcome!

Nice, will check it out!

Looks like my order from LCSC with the controller was lost lost in transit, or rather delivered to someone else. oh well...


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jjflash on December 21, 2020, 05:55:48 pm
Hello everyone,

I'm new here and in the first please excuse my extremly bad english. I'm a native speaken german. (Hi Tim, I see  :) you're staying here more often as in mikrocontroller.net).

So, why I'm writing the first post ever EEVblog has a simple reason (okay perhaps more reasons): At the first, thanks a lot to all the people who made it possible to handle with the ultra low cost Padauk controllers. I've build a Easy-PDK-Programmer :-) on breadboard and it works great, but due to the facts that a.) the used controller is currently rare and as a consequence of this, he is expensive.

The next thing ist, hobbiest aren't able to build a programmer what is a little bit pitty. So I thought an ATMega can do the job and I thought a lots of people have done such a thing, but terrifyingly I only found to projects to build a programmer that isn't based of the EASY-PDK. One is from socram8888 and I didn't get him to work. Voltage supply is the greatest problem, and the second project is from tim__ , sometimes it does the job and mor sometimes not.

So began to design an own ATmega based programmer for Padauk and I have done something like the Easy-Programmer with the voltages: An (old) switching regulator MC34063 works as a step-up converter und like Easy-Programmer I'll have an OP-Amp LM356 to generate the V_pp and V_dd. So, at the moment I can reliable flash a PFS154 Chip, but I can ONLY flash this type.

But... I want to flash a PFS173 too, and the second challenge begin. At the moment I can do :

- reading the device-ID (0EA2)
- erasing the device
- reading a word from the flash

But I cant write anything. After a write access not only one bit is writen. So I know, something with the protocol went wrong or something with the voltages (I use 8V for writing, 9V for erasing), or both went wrong.

So I'm slowly running out of ideas.

Has anywhere a documentation and / or oscillographs from the programming algorithm for PFS173 (like the analysis document on Tim's github https://github.com/cpldcpu/SimPad/blob/master/Protocol/PDKprogrammingsequence20v0.5.pdf )

-------------------------------------

So thanks a lot for reading ... and excuse the horrible english.

JJ / Ralph S.

Perhaps you want to have a look at my github ?

https://github.com/jjflash65/Padauk-pfs154
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 23, 2020, 05:57:02 pm
Hi jjflash,

as far as I remember the PFS173 uses the exact same protocol as the PFS154.

You can see the differences in "fpdkicdata.c" from the programmer software source code : https://github.com/free-pdk/easy-pdk-programmer-software/blob/master/fpdkicdata.c

I marked the differences (parameters and voltages) for you below:

  { .name                         = "PFS154",
    .otpid                        = 0x2AA1,
    .id12bit                      = 0xAA1,
    .type                         = FPDK_IC_FLASH_1,
    .addressbits                  = 13,
    .codebits                     = 14,
    .codewords                    = 0x800,
    .ramsize                      = 0x80,
    .exclude_code_start           = 0x7E0,  //OTP area 16 words, contains empty space for user and BGTR IHRCR factory values
    .exclude_code_end             = 0x7F0,
    .vdd_cmd_read                 = 2.5,
    .vpp_cmd_read                 = 5.5,
    .vdd_read_hv                  = 2.5,
    .vpp_read_hv                  = 5.5,
    .vdd_cmd_write                = 2.5,
    .vpp_cmd_write                = 5.5,
    .vdd_write_hv                 = 5.8,
    .vpp_write_hv                 = 8.5,
    .write_block_size             = 4,
    .write_block_clock_groups     = 1,
    .write_block_clocks_per_group = 8,
    .vdd_cmd_erase                = 2.5,
    .vpp_cmd_erase                = 5.5,
    .vdd_erase_hv                 = 3.0,
    .vpp_erase_hv                 = 9.0,
    .erase_clocks                 = 2
  },

  { .name                         = "PFS173",
    .otpid                        = 0x2AA2,
    .id12bit                      = 0xEA2,
    .type                         = FPDK_IC_FLASH_1,
    .addressbits                  = 13,
    .codebits                     = 15,
    .codewords                    = 0xC00,
    .ramsize                      = 0x100,
    .exclude_code_start           = 0xBE0, //OTP area 16 words, contains empty space for user and BGTR IHRCR factory values
    .exclude_code_end             = 0xBF0,
    .vdd_cmd_read                 = 2.5,
    .vpp_cmd_read                 = 5.5,
    .vdd_read_hv                  = 2.5,
    .vpp_read_hv                  = 5.5,
    .vdd_cmd_write                = 2.5,
    .vpp_cmd_write                = 6.5,
    .vdd_write_hv                 = 5.8,
    .vpp_write_hv                 = 9.0,
    .write_block_size             = 4,
    .write_block_clock_groups     = 1,
    .write_block_clocks_per_group = 8,
    .vdd_cmd_erase                = 2.5,
    .vpp_cmd_erase                = 5.5,
    .vdd_erase_hv                 = 3.0,
    .vpp_erase_hv                 = 9.0,
    .erase_clocks                 = 4
  },


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on December 24, 2020, 09:07:58 am
Hello,

first I want to thank you for the great work you did with the easy-pdk-programmer.

I build one myself month ago and did not have a problem so far. This week I updated the fireware from v1.1 to v1.3. At first it worked a bit, which means that erverything worked, but there was a noticeable delay from sending the probing/ereasing/writing command. Since the last days it does not work anymore. If I write the command nothing happens. The programmer is recognized under my Win7 PC as "STMicroelectronis Virtual COM Port"  in the device manager. It is also possible to flash an other firmware (I tried v1.1 with the relaiting exe, but that also did not work anymore). Could you please help me and tell me what I can try to get the programmer working again?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 24, 2020, 09:44:52 am
Hi KaeTo,

First thing to do: Run the programming in verbose mode (add the -v option to command line) and let us have a look at the output.

Next thing to try, compile "easypdkprogtest" from source (make easypdkprogtest).
Remove any attached IC from programmer and run easypdkprogtest. You should see an output like this one: "Vdd: 4.96   vpp: 4.98    (vref= 3.28)".
At the same time measure VDD and VPP on programmer header.
Please share your results (output of easypdkprogtest and measured results).

Edit: Just to make sure it's not a Windows quirks... Go to device manager of windows, remove the STM32 windows virtual com port device / driver and reinstall it. Another guess... can it be that you installed some "libusb" driver / software which now interferes with the standard COM port? Maybe you installed something for the DFU firmware update? (a driver uninstall/reinstall of the STM32 virtual com port should fix this as well)?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on December 24, 2020, 12:47:43 pm
I just tried it from another computer an the was no problem at all (with the same easypdkprog.exe). As soon as I am at home I will try it again. I think maybe the program is blocked (I used the exe from the releases and did not compile myself).

It seems like the programm had a problem with some of my other COM Ports (virtual bluetooth COM Ports), thats why it stuck at the search for the programmer
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 01, 2021, 09:42:46 am
I habe another program,

I already build up one programmer and now build some more as a gift and as spare. So far the boards seem to work and I could flash them with the firmware. Tee problem I have with the new boards is, that if I connect them to the PC they always enter the mode to program them. I could not figure out why till now. I measured the connections and they seem to be okay. If I press the botton for the programming mode I get 3.3V on Pins Boot0 und PA15, but if I release the button I get 1.0V instead of 0V. So far I testet the pulldown resistor and it is connected correct and also switched the 20k to 10k without result (only the measured voltage droped a tiny bit). I could not figure out what I did wrong. I have to of this boards which show the same behavior. THe only difference to my first and working pdk programmer ist the supplier of the chips. The first came from lcsc but the chips from the other boards came frome a seller from ebay, because I could not find the chip from any distributor (lcsc, mouser, digikey, ...). Could it be that I have got fake chips (but if thats the case it is strange that I could program them without a problem).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2021, 11:55:45 am
I just tried it from another computer an the was no problem at all (with the same easypdkprog.exe). As soon as I am at home I will try it again. I think maybe the program is blocked (I used the exe from the releases and did not compile myself).

It seems like the programm had a problem with some of my other COM Ports (virtual bluetooth COM Ports), thats why it stuck at the search for the programmer

Thanks for the info. In this case you also can specify the port directly on the command line (no autodetect).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 01, 2021, 12:00:44 pm
I habe another program,

I already build up one programmer and now build some more as a gift and as spare. So far the boards seem to work and I could flash them with the firmware. Tee problem I have with the new boards is, that if I connect them to the PC they always enter the mode to program them. I could not figure out why till now. I measured the connections and they seem to be okay. If I press the botton for the programming mode I get 3.3V on Pins Boot0 und PA15, but if I release the button I get 1.0V instead of 0V. So far I testet the pulldown resistor and it is connected correct and also switched the 20k to 10k without result (only the measured voltage droped a tiny bit). I could not figure out what I did wrong. I have to of this boards which show the same behavior. THe only difference to my first and working pdk programmer ist the supplier of the chips. The first came from lcsc but the chips from the other boards came frome a seller from ebay, because I could not find the chip from any distributor (lcsc, mouser, digikey, ...). Could it be that I have got fake chips (but if thats the case it is strange that I could program them without a problem).

Are you really sure you program the correct firmware? (sometimes people try to download files from github with "Save as..." and do not recognize that in fact a HTML is saved instead of the requested file.)

The output of DFU utility when you do the flashing will be helpful to investigate further.

Regarding the measured 1V at Boot 0 pin... In case you did not flash a valid firmware, the STM32 has detections for this to automatically enter bootloader (e.g. on complete blank chip or if the reset vector points to nirvana). After entering bootloader the processor is executing it's code which might cause some state of the BOOT 0 pin where in fact a pull up or output is coming from STM32.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 01, 2021, 06:05:12 pm
Yes I checked that thr flashing ist corect. I flashed the same firmware for both (my first and the new programmers). The firmware ist flashed and the progress bar reaches by all programmers the 100% and fineshes flashing.
What can I try next?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 02, 2021, 10:33:54 am
Yes I checked that thr flashing ist corect. I flashed the same firmware for both (my first and the new programmers). The firmware ist flashed and the progress bar reaches by all programmers the 100% and fineshes flashing.
What can I try next?

Can you provide the output of DFU util so we can have a look?

By any chance, do you have a STLinkV2 *or* a FTDI USB UART adapter?
With STLink V2 you can connect to SWD pins (4 pins on bottom of board next to the "freepdk" text) and read out to vertify the IC and/or flash the firmware directly with a special ST tool (STLink Tool)
Same can be done with a FTDI USB UART adapter and another special ST tool (Flash Loader Demonstrator).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 02, 2021, 04:32:17 pm

Can you provide the output of DFU util so we can have a look?


I attached a screenshot of the flashing in normal mode and a textfile with the output of the flashing in verbose mode.

I have a FTDI USB UART adapter. I tried the Flash Loader Demonstrator but I did not get it to work. How is the pinout on the programmer board? I checked the datasheet and the the schematic, but I only got GND,??, TX_UART2_STM32, VCC. ?? ist PINPA13 and has no UART function (only I/O and IR_OUT, SWDIO,USB_NOE) according to the datasheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 02, 2021, 10:56:46 pm
Your DFU flashing looks 100% correct.

Time to investigate what was actually written to IC.

EDIT: I just remembered that you can read back the IC with dfu-util.
Execute the following command
dfu-util -d 0483:df11 -a "@Internal Flash  /0x08000000/064*0002Kg" --dfuse-address 0x08000000 -U readout.bin
...
Opening DFU capable USB device...
ID 0483:df11
Run-time device DFU version 011a
Claiming USB DFU Interface...
Setting Alternate Setting #0 ...
Determining device status: state = dfuERROR, status = 10
dfuERROR, clearing status
Determining device status: state = dfuIDLE, status = 0
dfuIDLE, continuing
DFU mode device DFU version 011a
Device returned transfer size 2048
DfuSe interface name: "Internal Flash  "
Limiting upload to end of memory segment, 131072 bytes
Upload   [=========================] 100%       131072 bytes
Upload done.

And then compare the readout.bin file with the firmware.dfu file (they should be identical at the beginning). You also might ZIP and attach the readout.bin to your next post.

Will be interesting to hear your results, especially if the READ contains the flashed DFU or not (in case you only can read 0xFF and also 5.) does not change the situation it means the STM32 do have a bad flash - most likely by overheating them when soldering / unsoldering them in case they are used).

JS


BTW: LCSC has STM32F072 in stock again... the price is a bit crazy but it is available again.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 03, 2021, 09:22:49 am
Readout of the the programmer worked with dfu-util. I compared the working programmer, the two not working and the firmware file.
The file from the working programmer and the firmware were the same. The file from the two not working programmers had some clear text errors like "Flash WRP is not setting...", "Flash WRP setting error!", "Checksum FAIL!!", ...
Readout files 2 and 3 are frome the "defect" programmers, file 1 from the working.

Thank you for the hint with the to high temperature. The were new but at first I soldered them the wrong way and had to desolder them (280°C for a few minutes) to turn them the right way.

Could you tell me from the readout, if the flash is really bad and if I have to switch the uC?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 03, 2021, 12:27:33 pm
Readout of the the programmer worked with dfu-util. I compared the working programmer, the two not working and the firmware file.
The file from the working programmer and the firmware were the same. The file from the two not working programmers had some clear text errors like "Flash WRP is not setting...", "Flash WRP setting error!", "Checksum FAIL!!", ...
Readout files 2 and 3 are frome the "defect" programmers, file 1 from the working.

Thank you for the hint with the to high temperature. The were new but at first I soldered them the wrong way and had to desolder them (280°C for a few minutes) to turn them the right way.

Could you tell me from the readout, if the flash is really bad and if I have to switch the uC?

Hi,

Now we getting somewhere... The readout2 and readout3 show a complete different firmware. It looks like a Arduino / Bluepill / ... bootloader.

Most likely flash WRITE-PROTECTION has been set so this existing bootloader can not been overwritten by accident.

==> In order to write a new firmware to this used and locked ICs you have to clear the write protection.

I don't know how this is possible with DFU but I know for sure it is possible via UART bootloader.

For uart bootloader you need your FTDI adapter and connect:

FTDI_TX  ==> STM32_UART2_RX ==> PA13 ==> (solder wire to right side of push button)
FTDI_RX  ==> STM32_UART2_TX ==> PA14 ==> SWCLK
FTDI_GND ==> GND

The tool from ST can be found here:
https://www.st.com/en/development-tools/flasher-stm32.html (https://www.st.com/en/development-tools/flasher-stm32.html)

Start the ST Flash Loader Demonstrator, select the COM port from your connected FTDI adapter, click Next and if all goes well the STM32F072 is detected.
In case you can not detect the IC make sure, use a power bank or your phone charger and plug it into USB port of easy pdk programmer while holding the button.
(This prevents STM32 ROM bootloader to enter USB DFU which it would do in case USB activity is detected, instead it wait for UART connect which you will do with the ST tool).
Also you might need to exchange RX and TX (not sure how your FTDI adapter is labeled).

When STM32F072 was detected properly you can select a firmware to flash (you can use the DFU file directly - even that it asks you for bin file). When you try to flash it the ST tool will tell you that it needs to remove the WRITE PROTECTION, click on "yes" and this should do the trick.

==> This will finally reset your used STM32 to factory defaults and flash the new firmware. Since easypdk programmer firmware does not lock flash you can use DFU util to flash firmware updates later just like on a factory fresh IC.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 03, 2021, 01:15:58 pm

Start the ST Flash Loader Demonstrator, select the COM port from your connected FTDI adapter, click Next and if all goes well the STM32F072 is detected.
In case you can not detect the IC make sure, use a power bank or your phone charger and plug it into USB port of easy pdk programmer while holding the button.
(This prevents STM32 ROM bootloader to enter USB DFU which it would do in case USB activity is detected, instead it wait for UART connect which you will do with the ST tool).
Also you might need to exchange RX and TX (not sure how your FTDI adapter is labeled).

When STM32F072 was detected properly you can select a firmware to flash (you can use the DFU file directly - even that it asks you for bin file). When you try to flash it the ST tool will tell you that it needs to remove the WRITE PROTECTION, click on "yes" and this should do the trick.


I tried it with both not working programmer, but none of them was detected. I made sure the PINs are connected correctly and the power came from a phone charger. I also pressed the button while connection to power. The ST Flash Tool always ran in a timeout.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 03, 2021, 08:25:37 pm

Start the ST Flash Loader Demonstrator, select the COM port from your connected FTDI adapter, click Next and if all goes well the STM32F072 is detected.
In case you can not detect the IC make sure, use a power bank or your phone charger and plug it into USB port of easy pdk programmer while holding the button.
(This prevents STM32 ROM bootloader to enter USB DFU which it would do in case USB activity is detected, instead it wait for UART connect which you will do with the ST tool).
Also you might need to exchange RX and TX (not sure how your FTDI adapter is labeled).

When STM32F072 was detected properly you can select a firmware to flash (you can use the DFU file directly - even that it asks you for bin file). When you try to flash it the ST tool will tell you that it needs to remove the WRITE PROTECTION, click on "yes" and this should do the trick.


I tried it with both not working programmer, but none of them was detected. I made sure the PINs are connected correctly and the power came from a phone charger. I also pressed the button while connection to power. The ST Flash Tool always ran in a timeout.

Have you tried to swap RX / TX in case your FTDI adapter is labeled incorrectly?.

I just tried it myself and everything is working as expected.
I observed that I had to hold button, connect power and after this connect FTDI USB adapter to computer (otherwise TX line from FTDI was feeding some voltage to STM which was enough to start it...)

Attached some pictures / screen shots.

Don't get confused from the color of the wires in the picture: (WHITE = FTDI_RX , BLACK = FTDI_TX , BROWN = FTDI_GND)

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: pacmancoder on January 03, 2021, 08:57:32 pm
Hello there! I have implemented a software UART generator with Web UI available!
It generates C transmit and receive functions with (I hope?) clock-precise inline assembly code. Maybe It will be useful for someone  :D

Take a look at the page on my website:
https://pacmancoder.xyz/freepdk-uart-gen/

CLI version is also available, but it should be compiled from sources manually as I didn't prepare the release executables yet.

The generator itself is open-sourced at https://github.com/pacmancoder/freepdk-gen , so if anyone wants to improve it / use it as a base for other generators - welcome to the project's GitHub repo! Web UI glue code is currently a part of my personal website, but it is also open-sourced at https://github.com/pacmancoder/pacmancoder.github.io too.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on January 13, 2021, 05:09:32 am
When STM32F072 was detected properly you can select a firmware to flash (you can use the DFU file directly - even that it asks you for bin file). When you try to flash it the ST tool will tell you that it needs to remove the WRITE PROTECTION, click on "yes" and this should do the trick.

I finally got the programer running with the help of a friend. He had a STM programmer und with it it worked flawlessly. Now the programer behaves like expected.

Thank you for all your great help :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: C. Tracy on January 18, 2021, 04:38:47 am
Hello,
   1st of all, big thank you to everyone who worked on this incredible project.
   I have an issue, I have carefully assembled the Easy-pdk-programmer pcb 2 times (although I think I got PTSD from soldering it) and both times I get the same result; 9193-33 regulator (U2 on schematic) heats up rather quickly and PC does not recognize that a device has been plugged into USB. I can find no shorts or cold joints. Is it possible I cooked one of the components while soldering? I know this is super vague but any suggestions before I try to solder a 3rd board and ruin that one too would be great. Thanks.

*edit* I get less than 1 ohm of resistance across C5, C7, C8, C9, C12. That will mean that the Vout of the regulator is essentially shorted to ground (which explains why board doesn't start) but can't tell in-circuit what the issue is. seems like maybe I should try and re-solder the microcontroller because it has a bunch of pins where 3.3v and GND are adjacent, so most likely that is where the problem is?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2021, 07:27:32 am
I may have found a strange bug (feature?) in the IO ports of the PFS154.

I used the following code to switch a PGIO between logical high ("Hi") and high impedance state ("Z").

Code: [Select]
PA |=1<<4:

PAC |=1<<4;   // HI

PAC &=~(1<<4); // Z

This works fine. But if another port is accessed in between, it appears that the state of PA is lost?


Code: [Select]
PA |=1<<4:

PA |=1<<3;  // turn on PA3

PAC |=1<<4;   // This will not activate the pin anymore!

PAC &=~(1<<4); // Z

Very odd. Has anybody seen similar?

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2021, 07:43:23 am
Below you can find a very efficient code to implement an ADC with the internal resistor ladder based on the SAR principle. Maybe it is uselful to some.

It works well with the LRC clock (53 kHz main clock). I don't know how fast the comparator actually is, it may be neccessary to introduce wait states when clocking the CPU at a much higher frequency.

Code: [Select]
GPCC = GPCC_COMP_ENABLE | GPCC_COMP_MINUS_BANDGAP_1V2; // Activate comparator. Negative input is bandgap, positive input is resistor ladder

// SAR ADC using the internal resistor ladder
__asm
mov a, #0x20  ; GPCS.4 = 0  GPCS.5 = 1

or      a, #0x08   ; Bit 3
mov     __gpcs,a
t0sn    __gpcc, #6
xor     a, #0x08

or      a, #0x04   ; Bit 2
mov     __gpcs,a
t0sn    __gpcc, #6
xor     a, #0x04

or      a, #0x02   ; Bit 1
mov     __gpcs,a
t0sn    __gpcc, #6
xor     a, #0x02

or      a, #0x01   ; Bit 0
mov     __gpcs,a
t0sn    __gpcc, #6
xor     a, #0x01

and     a,#15 // Result is now in A register.

set0    __gpcc,#7  ; turn comparator off
                ret
__endasm;

p.s.: Only 3 instructions per bit would be needed of the resistor ladder had a R/W register. But alas, it's WO.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on January 18, 2021, 07:50:33 am
Hello,
   1st of all, big thank you to everyone who worked on this incredible project.
   I have an issue, I have carefully assembled the Easy-pdk-programmer pcb 2 times (although I think I got PTSD from soldering it) and both times I get the same result; 9193-33 regulator (U2 on schematic) heats up rather quickly and PC does not recognize that a device has been plugged into USB. I can find no shorts or cold joints. Is it possible I cooked one of the components while soldering? I know this is super vague but any suggestions before I try to solder a 3rd board and ruin that one too would be great. Thanks.

*edit* I get less than 1 ohm of resistance across C5, C7, C8, C9, C12. That will mean that the Vout of the regulator is essentially shorted to ground (which explains why board doesn't start) but can't tell in-circuit what the issue is. seems like maybe I should try and re-solder the microcontroller because it has a bunch of pins where 3.3v and GND are adjacent, so most likely that is where the problem is?

That sounds like a short indeed. Are you certain there are no solder bridges or similar? I guess you already started probing with your multimeter, that's definitely the way to go. DId you try to make some hi resolution photographs to check bad solder joints? May also help posting them here, becuase otherwise it's tough to tell what is wrong.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: C. Tracy on January 18, 2021, 01:58:47 pm
Tim_, thank you for your response. There was indeed a solder bridge between pin 8 and 9 of the stm32.  Don't know how I didn't see it last night.  My eyes must have been fatigued as I don't have a magnifier.  I tried to take pictures but they've come out super grainy, apparently my light or camera (or both) isn't up to the task.  But now I get about 40K of resistance across the caps, and an actual 3.3v (well 3.28 on the meter) output when plugged in.  PC however still doesn't recognize that anything has been plugged in.  Button is working at least I can tell that much.  I'll take this to work tonight and use their magnifier to inspect the board.  Somehow I think I'm going to end up soldering a 3rd. Again thanks for the response.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 19, 2021, 03:23:05 pm
I may have found a strange bug (feature?) in the IO ports of the PFS154.

I used the following code to switch a PGIO between logical high ("Hi") and high impedance state ("Z").

Code: [Select]
PA |=1<<4:
PAC |=1<<4;   // HI
PAC &=~(1<<4); // Z

This works fine. But if another port is accessed in between, it appears that the state of PA is lost?

Code: [Select]
PA |=1<<4:
PA |=1<<3;  // turn on PA3
PAC |=1<<4;   // This will not activate the pin anymore!
PAC &=~(1<<4); // Z

Very odd. Has anybody seen similar?

Hi,

I used your code, made a test program and compiled it to see the assembly output (in order to check if there is a compiler problem):

;   test.c: 14: PA |=1<<4;
   set1   __pa, #4
;   test.c: 16: PA |=1<<3;  // turn on PA3
   set1   __pa, #3
;   test.c: 18: PAC |=1<<4;   // This will not activate the pin anymore!
   set1   __pac, #4
;   test.c: 20: PAC &=~(1<<4); // Z
   set0   __pac, #4


Output looks 100% correct so not a compiler problem.

Next I wanted to check what you see and what to expect and I think I know what happens:

   set1   __pa, #4   ;PA.4 set 1 (but PA.4 was not setup as output before) ==> no output on PA.4

==> here I think might be your problem: In case PADIER.4 is set to 1 (PA.4 is a digital input) then with every SYSCLK? or "port access"? the content of PA.4 is assigned the value of the PIN PA.4 read as digital input. If the next instruction is your switch of PAC.4 then most likely there was no time? / no port access and therefore no update of PA.4. If you put instructions in between (which access the port?) then PA.4 might get updated with the digital input pin value.
 
   set1   __pa, #3   ;PA.3 set 1 (but PA.3 was not setup as output before) ==> no output on PA.3

   set1   __pac, #4 ;PAC.4 set 1 => PA.4 is output now, from now on you can write to PA.4 to set output values
   set0   __pac, #4 ;PAC.4 set 0 => PA.4 is input now, from now on PA.4 will update internally depending on input voltage


My guess would be a simple addition of:

  PADIER &= ~(1<<4);

at the beginning of your test code will most likely bring up the behavior you expect.
You also should consider explicitly setting up PAPH (disable pull high).

EDIT:
Details: Chapter "5.9 IO Pins" in PFS154 manual => see "Fig. 7: Hardware diagram of IO buffer"

After looking at the diagram the flip flops and the signals all is orchestrated by the MUX. There should be no influence of the value in the WR-flip-flop by any other port access.

EDIT2:

MAYBE, you use an older version of SDCC which in fact generates assembly instructions to "read port value, do arithmetic, write port value". Then the behavior would be explainable with a wrongly configured "PADIER".

Can you check the assembler output of your code if bit set/clr instructions or port reads are used?


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on February 04, 2021, 03:38:10 am
Hi everyone:
Padauk IDE 0.91 version. It update PDK "29" version
Don't depdk it?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 04, 2021, 03:37:45 pm
Hi everyone:
Padauk IDE 0.91 version. It update PDK "29" version
Don't depdk it?

Where did you get the "PDK 29 version" information from? Is this you Kent Lee?  ::)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vitohong on February 04, 2021, 04:10:10 pm
for using PMS150G,I download IDE 0.91 version.
"opossum" tool at this forum. Show PDK 29
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on February 05, 2021, 12:48:27 am
Hi JS:
code1: original
code2: oposum disassble
code3: your dispdk

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 06, 2021, 10:59:24 pm
Really.... ? ? ? ?

Self modifying code now in PADAUK IDE to "protect" the "obfuscation" and then the only "new" thing is xoring 4 different values from key and changing 0x12345678 to 0x123457AE ?

 :-DD

=> depdk / dispdk got support for IDE 0.91 pdk files (check github)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on February 07, 2021, 03:41:04 am
Really.... ? ? ? ?

Self modifying code now in PADAUK IDE to "protect" the "obfuscation" and then the only "new" thing is xoring 4 different values from key and changing 0x12345678 to 0x123457AE ?

 :-DD

=> depdk / dispdk got support for IDE 0.91 pdk files (check github)

JS

One has to wonder what the point of trying to make the file format "more secure" is anyways. I have not seen anyone trying to use a custom programmer with the PADAUK IDE. Or don't they want us to decode future instuction sets? As long as the programming algorithm is not encrypted I don't see a chance there...

One another note: It seems that the stock of Padauk MCUs at LCSC is depleting and they are not reordering? I enquired about the PFS154-S16 and they responded with the part being "unavailable". I also asked LCSC if they are planning to add some of the newer decices and it seems they had no plan to.

Is anyone aware of an alternative distributor that can be used as easily as LCSC? Taobao is quite a hassle when you are not living in china...


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on February 07, 2021, 09:59:16 am
I download the update tool
Already completely correct
Thanks JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on February 07, 2021, 10:46:02 am
I investigated the low power modes of the PFS154 a bit. Turns out the Padauks are actually quite competitive, even compared to "low power" 8 bit MCUs.

https://cpldcpu.wordpress.com/2021/02/07/ultra-low-power-led-flasher/

There were some some surprises to work around. One of them was that  all timers can be used to wake up from STOPEXE instead of only the 16 bit timer. This is not quite clear from the manual.

While investigating this, I measured the transient power consumption of the PFS154. (I used a self-made wide bandwidth transimpedance amplifier with JFET input to amplify the current). You can see an example of a power signature for LRC execution below. It appears that the Padauk is a true 1 cycle design. Both edges of the clock are used, supposedly for fetch/exec and write back. It should be possible to deduce information about the type of instructions being executed from the power trace, but I did not go deeper.

I also found that there is an active 8 bit counter in STOPEXE, even when all timers are turned off. Not sure if this is intentional. So if the Padauk designers read this, they may want to look into their clock-gating :) (Yes, I am complaining about 10µA transients that need maybe 1pC of charge).


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on February 14, 2021, 01:21:17 pm

It seems that LCSC has run out of all flash version of the Padauk controller. An inquiry came back with the info that these parts are unavailable. That's a pity, because they were the only supplier that was somewhat hassle-free. Also, none of the products that were released during 2020 every made it to LCSC. All the official distributors listed on padauk are actually rather small dealers on 1688 and taobao.

Looks like it will be very difficult to acquire new stock.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 14, 2021, 07:35:31 pm
Currently, you can still find some classic Padauk models from Aliexpress. I contacted some guys from Taobao, seems like they're also laking micros due to the high demand in Mainland China. I purchased a few hundreds of PMS150C from them. They're really friendly. If you have a WeChat account, you can add one or two official resalers as friends so you can get your padauk micros directly from them.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 14, 2021, 07:39:28 pm
Also, I got an official writer and in-circuit emulator. Now I can freely switch between FreePDK and their Mini-C :-+. If you guys want me to test anything like a new ic or capture some programming sequences, feel free to tell me! I have a basic level oscilloscope and a 24Mhz FX2LP logic analyzer.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 20, 2021, 08:51:23 am
Here's an update on the official writer. Padauk's official writer will enforce the difference between PMS150C and PMS15A. The writer will not write PMS150C's binary into a PMS15A.
If you modify .Assembly   User_Size   200h manually, the WRITER software will refuse to load the compiled binary.
One more point to FreePDK programmer!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 22, 2021, 10:12:30 am
Just saw this offer:

https://detail.1688.com/offer/521685377594.html

PADAUK IC combined with wireless sender/receiver (maybe something like a NRF24L01 clone).

Wireless remote control for <0.20 USD ? I guess a battery will cost more than the rest of this.

 :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 22, 2021, 02:51:16 pm
Padauk with wireless? That sounds like a nice combination. Seems like they offer multiple versions. Besides the PMS132 one, we can basically use them with FreePDK without any additional hard to gather hardware information.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: electronic_eel on February 22, 2021, 03:25:37 pm
While investigating this, I measured the transient power consumption of the PFS154. (I used a self-made wide bandwidth transimpedance amplifier with JFET input to amplify the current). You can see an example of a power signature for LRC execution below.
Could you show more details how you created this power trace with your JFET amplifier? What kind of bandwidth do you estimate for it?

I'm interested in doing similar measurements for low power optimization.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 22, 2021, 05:11:46 pm
A further thought on PMS15A and PMS150C: The die in PMS15A and PMS150C might be the same, the initial information stored in the OTP ROM might differ between these two ICs. And that's how the official Padauk programmer distinguishes these ICs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 22, 2021, 06:51:47 pm
A further thought on PMS15A and PMS150C: The die in PMS15A and PMS150C might be the same, the initial information stored in the OTP ROM might differ between these two ICs. And that's how the official Padauk programmer distinguishes these ICs.

There is no such thing as OTP-ROM. There is just the OTP area we can read. Since we also use the exact same sequence WRITER uses to check for PMS150C there is really not any difference.
Can you read a blank PMS15A of yours and share the readout "easypdkprog -n PMS150C -b read pms15aempty.bin".

It might be possible that at factory they do write "0" to some portions of the upper half of the OTP area and that is how WRITER detects it...

The PMS15A I bought do not differ in a single bit from PMS150C.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on February 23, 2021, 10:45:55 am
Can you read a blank PMS15A of yours and share the readout "easypdkprog -n PMS150C -b read pms15aempty.bin".

There are differences between 150C and 15A's readouts. From 0x7Ec to the end of the binary file.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on February 24, 2021, 08:55:05 am
They are different  fab.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 24, 2021, 01:09:23 pm
Can you read a blank PMS15A of yours and share the readout "easypdkprog -n PMS150C -b read pms15aempty.bin".

There are differences between 150C and 15A's readouts. From 0x7Ec to the end of the binary file.

Thanks for the readout. Looks like 2 single bytes are written in reserved area so WRITER can determine if it is a PMS15A labeled PMS150C.
This also means we still can use PMS15A as a full featured PMS150C (just missing 2 bytes in reserved area which we can not program anymore - no loss at all).

 :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on March 14, 2021, 02:35:15 pm
I've been experimenting with the PMS150c recently, and I have hit a snag: What's the correct way to initialize Timer16 to fire an interrupt in assembly?

Here's my attempt (full code attached):

Code: [Select]
        ;XXX: timer16 setup -- this is broken
        mov     a, #(( 1<<0 | 1<<3 | 4<<5 ))    ; ovf@bit9, clk/4, ihrc
        mov     t16m, a
        mov     a, #2           ; enable timer16 int, disable all others
        mov     inten, a
        ; ...
        engint

I want timer16 to cause an interrupt every 512 cycles. The IVR then changes the PWM duty cycle of timer2 (timer2 works).

Looking at the generated code (with dispdk, also attached), it seems like it should work :/

Thanks in advance for any help!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 14, 2021, 07:05:36 pm
I've been experimenting with the PMS150c recently, and I have hit a snag: What's the correct way to initialize Timer16 to fire an interrupt in assembly?

Here's my attempt (full code attached):

Code: [Select]
        ;XXX: timer16 setup -- this is broken
        mov     a, #(( 1<<0 | 1<<3 | 4<<5 ))    ; ovf@bit9, clk/4, ihrc
        mov     t16m, a
        mov     a, #2           ; enable timer16 int, disable all others
        mov     inten, a
        ; ...
        engint

I want timer16 to cause an interrupt every 512 cycles. The IVR then changes the PWM duty cycle of timer2 (timer2 works).

Looking at the generated code (with dispdk, also attached), it seems like it should work :/

Thanks in advance for any help!

Hi


   mov     a, #2 ; enable timer16 int, disable all others  <== here is most likely your error, T16 int is BIT2  = 1<<2 =  4  ==> mov a, #4
   mov     inten, a


In case you like some more comments:

* your setup of TM16 is wrong, according to your comment you want every 512 cycles to get an interrupt. For this you need to setup BIT8 overflow (see data sheet: "9.2.5.   TIMER time out" for full details)

* your comment about "no calibration" is incorrect. In fact without setting IHRCR it will stay 0 after reset which causes for IHRC/4 something around 2.5MHz instead of the 4MHz (this also affects your PWM timing)

* your interrupt does not have the pushaf / popaf (this could cause problems if you ever add some more code to your "loop")

* pac all set as output will not save power... (unused pins should be set as input)

* you cold save the the extra variable and some instructions if you use tm2b directly and add 4 to it (mov a, tm2b    add a,#4   mov tm2b, a)


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on March 14, 2021, 08:50:29 pm
hi, js!

here is most likely your error, T16 int is BIT2  = 1<<2 =  4  ==> mov a, #4

Oh, wow, what an embarrassing mistake! Thanks, that fixed it!

In case you like some more comments:

i do!

* your setup of TM16 is wrong, according to your comment you want every 512 cycles to get an interrupt. For this you need to setup BIT8 overflow (see data sheet: "9.2.5.   TIMER time out" for full details)

Again, thanks. Off by one! I do wonder, though: shouldn't bit8 flip at value 256? (i have read the datasheet, i just think that's unintuitive)

* your comment about "no calibration" is incorrect. In fact without setting IHRCR it will stay 0 after reset which causes for IHRC/4 something around 2.5MHz instead of the 4MHz (this also affects your PWM timing)

I noticed that it was way too slow; I intend to use the instructions from the EASY_PDK_CALIBRATE_RC_M macro once I got the other parts working. And while i have your attention: I guess, just pasting those ANDs in and removing the --nocalibrate flag is enough? And I assume it's possible to calibrate to "odd" values, like 4.096MHz?

* your interrupt does not have the pushaf / popaf (this could cause problems if you ever add some more code to your "loop")

am aware, was just too lazy for this test.

* pac all set as output will not save power... (unused pins should be set as input)

good to know, thanks!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 14, 2021, 11:22:43 pm

* your comment about "no calibration" is incorrect. In fact without setting IHRCR it will stay 0 after reset which causes for IHRC/4 something around 2.5MHz instead of the 4MHz (this also affects your PWM timing)

I noticed that it was way too slow; I intend to use the instructions from the EASY_PDK_CALIBRATE_RC_M macro once I got the other parts working. And while i have your attention: I guess, just pasting those ANDs in and removing the --nocalibrate flag is enough? And I assume it's possible to calibrate to "odd" values, like 4.096MHz?

The macro takes 4 parameter: type, frequency, voltage and the register offset of IHRCR.

The tuning is using SYSCLK as reference. So if you want 4MHz sysclock then you have to setup CLKMD first and right after that you insert the "magic ANDs". The immediate values of the ANDs are used to encode the 4 parameter.

   
  ; clock setup (no calibration):
  set1  clkmd, #4       ; enable IHRC
  mov  a, #(( 0<<5 | 1<<4 | 0<<3 | 1<<2 | 0<<1 | 0<<0 ))
  mov  clkmd, a         ; switch to IHRC/4, WDT off; keep ILRC on

  ; calibration placeholder and parameters
  and a, #'R'
  and a, #'C'
  and a, #1                ;type 1 = IHRC calibration
  and a, #( 4194304 )      ;4MHz = 4194304Hz
  and a, #( 4194304>>8 )
  and a, #( 4194304>>16 )
  and a, #( 4194304>>24 )
  and a, #( 5000 )         ;5V = 5000mV
  and a, #( 5000>>8 )
  and a, #0x0B             ;register offset of IHRCR


The magic ANDs (will act as NOPs) been chosen that any programmer can still write the code and even if no calibration is performed the IC will still work (wrong frequency, but works).
EasyPDK programmer will replace them before writing with calibration code which is altered again after calibration.

You can *try* to calibrate to any value in Hz... just keep in mind that the IC is not very precise. If you are unlucky it is off by +-20kHz. It also drifts a lot by temperature change (just touching the IC is enough) or voltage change (always tune to the intended target voltage).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on March 20, 2021, 08:18:05 am
Hi everyone:
I compile calib-and-fuse-demo.c.

It generate asm
;   calib-and-fuse-demo.c: 41: EASY_PDK_CALIBRATE_IHRC(8000000,5000);        //tune SYSCLK to 8MHz @ 5.000V
   and   a, #'R'                       
   and   a, #'C'                       
   and   a, #((1))         
   and   a, #((8000000))     
   and   a, #((8000000)>>8) 
   and   a, #((8000000)>>16)
   and   a, #((8000000)>>24)
   and   a, #((5000))     
   and   a, #((5000)>>8) 
   and   a, #((0x0B))   

I confuseit
 
When I use program PMS150 OTP, how to calibration IHRC?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 20, 2021, 09:00:43 am
Hi everyone:
I compile calib-and-fuse-demo.c.

When I use program PMS150 OTP, how to calibration IHRC?

Hi,

easypdkprog will automatically detect the "magic AND sequence" and insert calibration code during programing. You have to do nothing special. Just write it using easy easypdkprog.

Output will look like this

easypdkprog --icname=PMS150C write calib-and-fuse-demo.ihx
Writing IC... done.
Calibrating IC (@5.00V IHRC SYSCLK=8000000Hz)... calibration result: 7946104Hz (0x84)  done.


JS

Please make sure that you use the LATEST version of easypdkprog (1.3 as of writing this) => https://github.com/free-pdk/easy-pdk-programmer-software/releases
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on March 20, 2021, 09:59:08 am
Thank JS.
Attached file, it 's Padaud calibration procoess Waveform.

where find it's asm at easy-pdk-programmer-software?

Hong
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on March 20, 2021, 10:31:17 am
One more update regarding Padauk's IDE.
If you don't allow Padauk IDE to access the internet or use an old version after a specific date, the IDE will throw all sorts of artificial(fake) errors to prevent you from using it.

That's not really nice I'll say...

Also, Kent should really review his English in Padauk's IDE...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vitohong on March 20, 2021, 12:15:03 pm
I use  ide 0.89 vs 0.91 .
0.84 didn't  internet.
0.91 have to use internet.
Then I want to know free PDK how to calibrate ihrc
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on March 20, 2021, 02:24:30 pm
Then I want to know free PDK how to calibrate ihrc
I think these are all you'll need. Not as simple as ".ADJUST_IC SYSCLK=IHRC/2;" but you get more control over the calibration process.
If you check sysclock.h and auto_sysclock.h you'll get more information.
Code: [Select]
unsigned char _sdcc_external_startup(void)
{
    // example, edit to suit
    AUTO_INIT_SYSCLOCK();
    AUTO_CALIBRATE_SYSCLOCK(TARGET_VDD_MV);
    return 0;                                 //perform normal initialization
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on March 20, 2021, 02:58:17 pm
thanks,
I find "fpdkiccalib.c"

  { .sopc=0x1442, .smsk=0xFFFF, .copc=0x1709, .cocf=CO_AC_NOP},                                //search: AND A, 'B'            /   calib: MOV A, 0x09                /   after-calib: NOP
    { .sopc=0x1447, .smsk=0xFFFF, .copc=0x0091, .cocf=CO_AC_NOP},                                //search: AND A, 'G'            /   calib: MOV IO(0x11), A  (PAC)     /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x0F8D, .cocf=CO_AC_NOP|CO_VAL_CAL_TYP},                 //search: AND A, *   (CAL_TYP)  /   calib: SET1 IO(0x0D).4  (PADIER.4)/   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x1784, .cocf=CO_AC_NOP|CO_VAL_MVOL_00},                 //search: AND A, *   (MVOL_00)  /   calib: MOV A, 0x84                /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x0080, .cocf=CO_BC_SETREG1|CO_AC_NOP|CO_VAL_MVOL_08},   //search: AND A, *   (MVOL_08)  /   calib: MOV IO(0x00), A  (SETREG1) /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x17A3, .cocf=CO_AC_NOP|CO_VAL_CAL_REG0},                //search: AND A, *   (CALREG0)  /   calib: MOV A, 0xA3                /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x0080, .cocf=CO_BC_SETREG2|CO_AC_NOP|CO_VAL_CAL_REG1},  //search: AND A, *   (CALREG1)  /   calib: MOV IO(0x1E), A  (SETREG2) /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFF00, .copc=0x17FF, .cocf=CO_AC_SETIMM|CO_VAL_CAL_REG2},             //search: AND A, *   (CALREG2)  /   calib: MOV A, 0xFF                /   after-calib: MOV A, <val>
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x0F70, .cocf=CO_AC_NOP},                                //search: AND A, 0              /   calib: SET1 IO(0x10).3  (PA.3)    /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x0080, .cocf=CO_BC_SETREG0},                            //search: AND A, 0              /   calib: MOV IO(0x00), A  (SETREG0) /   after-calib: stay
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x0C90, .cocf=CO_AC_NOP},                                //search: AND A, 0              /   calib: T0SN IO(0x10).4  (PA.4)    /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x1001, .cocf=CO_AC_NOP},                                //search: AND A, 0              /   calib: ADD A, 0x01                /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x0E70, .cocf=CO_AC_NOP},                                //search: AND A, 0              /   calib: SET0 IO(0x10).3  (PA.3)    /   after-calib: NOP
    { .sopc=0x1400, .smsk=0xFFFF, .copc=0x1808, .cocf=CO_BC_FIXUP|CO_AC_NOP},                    //search: AND A, 0              /   calib: GOTO 0x008       <FIXUP>   /   after-calib: NOP


Yes, It 's magic code than Padauk.  :-DD

Hong

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on March 20, 2021, 09:16:14 pm
Calibration worked perfectly, thanks for the explanation.

Next, and hopefully last 2 issues: my Timer16 interrupt is triggered twice in a row, and sometimes is offset. I attached a screenshot; the blue channel goes high whenever the IVR is active. And there are always two peaks next to each other. Also, it looks like it is "jittering" a lot: the interrupt is triggered early/late by the exact duration of a double-trigger (the double-double-peak on the left is "persistent phosphor" from two runs in a row...if that makes sense).

I am wondering what those two issues could be caused by and how to prevent them. The datasheet mentions that the T16 interrupt happens whenever the bit _changes_, but that should also be at regular intervals, not directly after the IVR was exited.


PS:
  and a, #( 4194304 )      ;4MHz = 4194304Hz
AFAIK, MHz is defined as 10^6, not as 2^20. so 4MHz should be 4000000Hz.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on March 21, 2021, 05:41:20 am
Hi gir:
I run your test file.
It's fine

Hong
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 21, 2021, 04:00:45 pm
Calibration worked perfectly, thanks for the explanation.
  and a, #( 4194304 )      ;4MHz = 4194304Hz
AFAIK, MHz is defined as 10^6, not as 2^20. so 4MHz should be 4000000Hz.
I know that... I gave this example since you asked for fractional MHz frequency value like 4.096MHz. I just forgot to update the comment ;-)

Next, and hopefully last 2 issues: my Timer16 interrupt is triggered twice in a row, and sometimes is offset. I attached a screenshot; the blue channel goes high whenever the IVR is active. And there are always two peaks next to each other. Also, it looks like it is "jittering" a lot: the interrupt is triggered early/late by the exact duration of a double-trigger (the double-double-peak on the left is "persistent phosphor" from two runs in a row...if that makes sense).

I am wondering what those two issues could be caused by and how to prevent them. The datasheet mentions that the T16 interrupt happens whenever the bit _changes_, but that should also be at regular intervals, not directly after the IVR was exited.

I observed a similiar behaviour some time ago and it all came down to the "stopexe" instruction.

I never had the time to fully investigate on this. I never got rid of the jitter.
My solution back then was to set SYSCLK to ILRC and not using stopexe at all.

I guess another interrupt might be triggered when the IC wakes up again. Maybe your "lazy" interrupt which does not check for the interrupt source causes the double execution.


JS

PS: Since stopexe makes use of ILRC (32 ILRC clocks when using faste wakeup) you should tune IHRC and ILRC (have a look in calib-and-fuse-demo.c inside of the examples folder from easypdk programmer). In general, if you want to tune ILRC you have to setup CLKMD for ILRC and add another tuning sequence (this time type=2). So if you want to tune ILRC and IHRC then you set ILRC as sysclk, add ILRC tuning sequence then directly afterwards set IHRC as sysclk and add IHRC tuning sequence.

Edit2: Just found in the manual:
http://www.padauk.com.tw/upload/doc/PMS15A,PMS150C%20datasheet%20V108_EN_20200724.pdf (http://www.padauk.com.tw/upload/doc/PMS15A,PMS150C%20datasheet%20V108_EN_20200724.pdf)
chapter 9.2.2 Interrupt:
(1)  When using the interrupt function, the procedure should be:
Step1: Set INTEN register, enable the interrupt control bit
Step2: Clear INTRQ register
Step3: In the main program, using ENGINT to enable CPU interrupt function
Step4: Wait for interrupt. When interrupt occurs, enter to Interrupt Service Routine
Step5: After the Interrupt Service Routine being executed, return to the main program
(2)  INTEN and INTRQ have no initial values. Please set required value before enabling interrupt function.


Edit: @homeworkboy / vitohong
Hi gir:
I run your test file.
It's fine
Hong
The problem is related to PMS150C. Do you say you can run it on PMS150C with stopexe and without jitter? Maybe your resolution of the logic analyzer is not high enough.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 21, 2021, 04:55:52 pm
thanks,
I find "fpdkiccalib.c"
...
Yes, It 's magic code than Padauk.  :-DD

Thanks. But you can not compare full source code with comments ("fpdkiccalib.c") to NO-CODE-AT-ALL (Padauk).

The code in fpdkiccalib.c is not very difficult to understand you just need to spend some minutes in the file. In case you have specific questions feel free to ask.
Unlike some other "magicians" I will fully reveal what other would call "magic".  8)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on March 24, 2021, 06:10:15 pm
Just a status update: I'm still working on my interrupt routine. removing stopexe from the main loop made the ISR trigger constantly (reducing the delay loop variable increases the interrupt frequency), so there's definitely something wrong with my understanding of how the ISR triggers. I tried to add the following check whether the right interrupt was triggered, but that prevented the routine from running at all.

        t1sn    intrq, #(1<<2)  ; if intrq.t16 is triggered, skip next
        reti  ; or alternatively, 'goto isr_end'


Using the ISR below, I checked which bits are set in intrq (it's 68 pulses, so bit 6 (timer2) and bit 4 (timer16)):

interrupt:
        push    af
        mov a, intrq
isr_number_loop:
        set1 pa, #6
        nop
        nop
        nop
        nop
        nop
        nop
        set0 pa, #6
        nop
        nop
        nop
        nop
        nop
        nop
        dzsn a
        goto isr_number_loop

        mov a, #0x3f
delayloop:
        dzsn a
        goto delayloop

isr_end:
        mov a, #0       ; clear all interrupts
        mov intrq, a    ; clear all interrupts
        pop     af
        reti



I don't expect you to fix that for me, js, just writing down my thoughts here.

Bonus link: a small software startup from Redmond has started using the pms150c: https://github.com/microsoft/jacdac-padauk (uses the proprietary IDE, though :/ )
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 24, 2021, 08:46:42 pm
Hi,

The IRQ logic is outlined in detail in the data sheet.

TM2 sets INTRQ regardless of enabling or disabling TM2 interrupt.

However the interrupt is only triggered when INTEN is enabled for TM2.


I try to explain it in short:

All the specific "peripherals" (TM16, TM2, ...) will do their stuff and set their INTRQ.

Then there is an AND logic with INTEN  and in case INTRQ.TM2 AND INTEN.TM2 is both 1 then interrupt will be triggered.

When you leave the interrupt and it happens that  INTRQ.TM2 AND INTEN.TM2 are still both 1 then the interrupt is triggered immediately again (the normal program will get no chance to execute anything).

In case you spend to much time in interrupt this also could cause the next INTRQ to be set already which could lead to constant interrupt triggering (when you clear INTRQ at begin of IRQ) or missed interrupt (when you clear INTRQ at end of interrupt).


So let's check the effective frequency and timing of your TM16:

   ;timer16 setup
   mov   a, #(( 0<<0 | 1<<3 | 4<<5 ))   ; ovf@bit8, clk/4, ihrc
   mov   t16m, a


* IHRC/4 = 4 MHz   =>  4 MHz / 512 = 7812 Hz
* SYSCLK = 4 MHz

=> The interrupt has max 512 cycles to execute.

Calculation of cycles consumed from your interrupt:
- int vector @0x10 contains a jump (2 cycles) to your interrupt code
- pushaf (2 cycles)
- mov a, intrq (1 cycle)

LOOP (in your case executed 68 times)
- set1,nop,nop,...,set0,nop,nop (14 cycles)
- dzsn (1 cycle)
- goto (2 cycles)

- mov (1 cycle)
- mov (1 cycle)
- popaf (1 cycle)
- reti (2 cycles)

= 2+2+1+68*(14+1+2)+1+1+1+2 = 1166 cycles   <== this is way more than the 512 cycles you have, means that 2  TM16 interrupts been missed already

This might be the reason that you observe the strange looking interrupt behavior.

JS

EDIT: In case you share a bit more of your final requirement then there might be even better / easier ways to achieve this. For the purpose shown in your example you just could use TM2 alone, generating an IRQ whenever one PWM cycle is over, in IRQ count a variable up to 4 and then change the PWM output value.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on March 30, 2021, 04:10:03 pm
Hello,

I build the pdk programmer a few times, but 2 of the programmer do not work. I can interface the STMs but cant programm or probe the padauk uCs. I run the easypdkprogtest from github and got as an result
vdd: 13.65   vpp: 13.55    (vref= 3.29)

Thanks JS, I managed to flash the Dev branch to the ARM and now it's working, But still only probing is working |O |O |O any Idea what might goes wrong?

Now you have to check your hardware variant. On the picture I saw that C1 is not populated and also Y1 is missing. A cap on the 15V rail is essential since VCC/VDD draw some power during programing. The crystal is used to get better tuning results after the CPU is flashed, without it the drift might be much higher or you create a very special clock path using the HSI48 with sync to USB frames (then programmer can not be used stand alone - a feature planned for future use, just like WRITER).

Also, since you changed the opamp, it might be possible that the output voltages differ. You can use the "easypdkprogtest" program to check that the output voltage is correct:

DO THIS WITHOUT A MCU CONNECTED TO THE PROGRAMMER

make easypdkprogtest

./easypdkprogtest
vdd: 5.01   vpp: 4.98    (vref= 3.30)


Please check that VDD and VPP are 5V and VREF is 3.3V. Also measure them on your PCB.

In case VDD and VPP voltages are incorrect you need to tune the DAC reference values for your specific hardware (in fpdk.c you need to change FPDK_VDD_DAC_MAX_MV / FPDK_VPP_DAC_MAX_MV).


JS


I found this post here so I assume that something is wrong with my programmer. What can I do or check next? (As Tools I have an lab bench power supply, an oscilloscop and a multimeter)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 30, 2021, 10:40:18 pm
Hello,

I build the pdk programmer a few times, but 2 of the programmer do not work. I can interface the STMs but cant programm or probe the padauk uCs. I run the easypdkprogtest from github and got as an result
vdd: 13.65   vpp: 13.55    (vref= 3.29)

Thanks JS, I managed to flash the Dev branch to the ARM and now it's working, But still only probing is working |O |O |O any Idea what might goes wrong?

Now you have to check your hardware variant. On the picture I saw that C1 is not populated and also Y1 is missing. A cap on the 15V rail is essential since VCC/VDD draw some power during programing. The crystal is used to get better tuning results after the CPU is flashed, without it the drift might be much higher or you create a very special clock path using the HSI48 with sync to USB frames (then programmer can not be used stand alone - a feature planned for future use, just like WRITER).

Also, since you changed the opamp, it might be possible that the output voltages differ. You can use the "easypdkprogtest" program to check that the output voltage is correct:

DO THIS WITHOUT A MCU CONNECTED TO THE PROGRAMMER

make easypdkprogtest

./easypdkprogtest
vdd: 5.01   vpp: 4.98    (vref= 3.30)


Please check that VDD and VPP are 5V and VREF is 3.3V. Also measure them on your PCB.

In case VDD and VPP voltages are incorrect you need to tune the DAC reference values for your specific hardware (in fpdk.c you need to change FPDK_VDD_DAC_MAX_MV / FPDK_VPP_DAC_MAX_MV).


JS


I found this post here so I assume that something is wrong with my programmer. What can I do or check next? (As Tools I have an lab bench power supply, an oscilloscop and a multimeter)

Your VDD is much to high (Should be 5V). Check the resistor R6, most likely you used the wrong value there.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on March 31, 2021, 03:38:14 am
I already checked R6. It has the correct value and is also solderd correctly.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 31, 2021, 07:22:03 am
I already checked R6. It has the correct value and is also solderd correctly.

In this case most likely the opamp U3 is damaged.

While running easypdkprogtest measure with your multimeter in DC voltage mode (one lead connected to GND):

U3:

pin8: 14.9V
pin4: -2.6V

pin3: 2.5V
pin2: 2.5V
pin1: 5V

pin5: 1.18V
pin6: 1.18V
pin7: 5V


What are your values?

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on March 31, 2021, 07:52:24 am
I already checked R6. It has the correct value and is also solderd correctly.

In this case most likely the opamp U3 is damaged.

While running easypdkprogtest measure with your multimeter in DC voltage mode (one lead connected to GND):

U3:

pin8: 14.9V
pin4: -2.6V

pin3: 2.5V
pin2: 2.5V
pin1: 5V

pin5: 1.18V
pin6: 1.18V
pin7: 5V


What are your values?

JS

My values are:

U3:

pin8: 15.0V
pin4: 4.5V

pin3: 3.8V
pin2: 6.2V
pin1: 13.7V

pin5: 3.8V
pin6: 3.82V
pin7: 13.6V
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on March 31, 2021, 05:35:06 pm
I already checked R6. It has the correct value and is also solderd correctly.

In this case most likely the opamp U3 is damaged.

While running easypdkprogtest measure with your multimeter in DC voltage mode (one lead connected to GND):

U3:

pin8: 14.9V
pin4: -2.6V

pin3: 2.5V
pin2: 2.5V
pin1: 5V

pin5: 1.18V
pin6: 1.18V
pin7: 5V


What are your values?

JS

My values are:

U3:

pin8: 15.0V
pin4: 4.5V

pin3: 3.8V
pin2: 6.2V
pin1: 13.7V

pin5: 3.8V
pin6: 3.82V
pin7: 13.6V

pin4: 4.5V <=== this should be a negative voltage !

==> check C14 / D2 / D3 / C3   - most likely the diodes are not soldered properly or in wrong orientation.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on April 01, 2021, 03:39:21 am

pin4: 4.5V <=== this should be a negative voltage !

==> check C14 / D2 / D3 / C3   - most likely the diodes are not soldered properly or in wrong orientation.

JS

Than kyou verry, very much. I found the problem only with your help. On one PCB I placed one diode in the wrong direction and on the other PCB there was a bad solder joint with the diode. Now both PCB are working fine :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on April 11, 2021, 09:33:35 am
Hi:
I compile pdk13 asm at PMS150

flow:
sdaspdk13 -losx sram.asm
sdldpdk  -i -m -x -u  sram
packihx sram.ihx > sram.hex

at sram.lst

      00004E 50 1C                   73   call push0
      000050 2A 18                   74    goto loop
It's correct.

but ihex
call  push0 -> call 0x28
goto loop   -> call 0x30

"sdlpdk -i -m -x -u sram"
Is the parameter setting wrong?

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 11, 2021, 03:15:04 pm
Hi:
I compile pdk13 asm at PMS150

flow:
sdaspdk13 -losx sram.asm
sdldpdk  -i -m -x -u  sram
packihx sram.ihx > sram.hex

at sram.lst

      00004E 50 1C                   73   call push0
      000050 2A 18                   74    goto loop
It's correct.

but ihex
call  push0 -> call 0x28
goto loop   -> call 0x30

"sdlpdk -i -m -x -u sram"
Is the parameter setting wrong?

Looks like you get confused by the SDCC assembler .LST format. SDCC uses/shows byte positions as addresses. When you disassemble the .IHX file with dispdk it shows the real code word positions like they are encoded in PDK opcodes.

1 PDK codeword (13-16 bit) = 2 bytes (2x 8 bit)

This means

SDCC .LST file : "00004E 50 1C                   73   call push0"

==> 0x50 / 2 = 0x28

REAL OPCODE / Disassembly: "call 0x28"

So everything is good.

JS


EDIT: I just spotted that your ".org 0x050" overwrites the already placed opcode for "goto loop" at 0x050 and your interrupt at 0x052. Maybe that's why your program is not working and you suspect the assembler for doing wrong things.

Please keep in mind SDCC .org directive is also BYTE based which means you have to multiply your real opcode positions by 2. In fact org 0x001, 0x003, 0x005, ... are INAVLID and can not be used at all.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on April 12, 2021, 01:47:29 am
Hi JS:
I got it ;D, thank you.

Hong
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 21, 2021, 08:05:54 pm
Some interesting development.

I added support for PMS150G (in development branch).

Looks like PMS150G / PMS15B has now an additional security feature: "instruction word scrambling".
This scrambling will shuffle the bits of an instruction word around (like a substitution cipher).

First I thought somebody made a mistake and wired the codemem data bus incorrectly and this is what is needed to fix the issue.
But later I found that only 32 instructions are scrambled, followed by 32 clear instructions, followed by 32 scrambled instructions, followed by 32 clear instructions, ...
So this was done on purpose.
This 1/2 security perfectly matches the already established 7/8 security.   :-DD
Also the bit pattern for bits without shifting is 55AA  (PADAUK must be really in love with that number). :-DD

@PADAUK: Thanks for this hardware challenge, but you can increase difficulty a bit...

The scramble pattern for PMS150G is: "0123f5b78da6c9e4"

(The pattern uses the hex digit to specify the bit pos where to get it from. e.g. "01234567890ABCDEF" will produce the same output as the input; "FEDCBA9876543210" will reverse a 16 bit value)

The implementation of the scrambler / descrambler is part of easypdkprog (development branch). Any read or write operation will transparently handle scrambling / descrambling. It's like there is no scrambling ;-)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on April 22, 2021, 03:13:24 am
HI JS:
how to find ""0123f5b78da6c9e4".
It look random data.


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 22, 2021, 07:24:48 am
HI JS:
how to find ""0123f5b78da6c9e4".
It look random data.

Just like you reverse any substitution cipher: https://en.wikipedia.org/wiki/Substitution_cipher
via a known plaintext attack: https://en.wikipedia.org/wiki/Known-plaintext_attack

1. you use WRITER to write a program which contains values with only one bit set: 0x0001 0x0002 0x0004 0x0008 ... 0x0800 0x1000
2. you read back the data using easypdkprog
3. you see the mapping of every bit:

scrambled(read via easypdkprog) => original (in PDK file)

*not part of 13 bit command*
0x8000 => 0x8000  (0b1000000000000000 => 0b1000000000000000) => "0"  (numeric value of bit position in original)
0x4000 => 0x4000  (0b0100000000000000 => 0b0100000000000000) => "1"
0x2000 => 0x2000  (0b0010000000000000 => 0b0010000000000000) => "2"
*13 bit command*
0x1000 => 0x1000  (0b0001000000000000 => 0b0001000000000000) => "3"
0x0800 => 0x0001  (0b0000100000000000 => 0b0000000000000001) => "f"
0x0400 => 0x0020  (0b0000010000000000 => 0b0000000000100000) => "5"
...
0x0002 => 0x0002  (0b0000000000000010 => 0b0000000000000010) => "e"
0x0001 => 0x0800  (0b0000000000000001 => 0b0000100000000000) => "4"
 
==> "0123f5...e4"

It's like SUDOKU for advanced  8).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on April 22, 2021, 09:15:43 am
HI JS:
I feel what Padauk is doing is a wild-goose chase
 ;D
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 22, 2021, 09:35:11 am
Congratulations on the PMS150G!
Now the question is: how do we compile for PMS150G?
This chip contains a few additional features than PMS150C(e.g. PA5 can be used as a push-pull pin) but it runs slower(2MB).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 22, 2021, 05:24:57 pm
Congratulations on the PMS150G!
Now the question is: how do we compile for PMS150G?
This chip contains a few additional features than PMS150C(e.g. PA5 can be used as a push-pull pin) but it runs slower(2MB).

You program it just like any other IC.

Have a look in the "Examples" folder of easypdkprog. There you can find the "helloworld2mhz.c" program and in "Examples/src/easypdk" folder you have a fully adapted "pms150g.h" include file.

For example, if you want to setup PA5 as PP then you only have to set the correct FUSE value.

You can place this (after sysclock setup and calibrate):

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_2MHZ();
  EASY_PDK_CALIBRATE_IHRC(2000000,4000);        //tune SYSCLK to 2MHz @ 4.000V
  EASY_PDK_FUSE(FUSE_SECURITY_OFF | FUSE_LVR_1V8 | FUSE_IO_DRV_NORMAL | FUSE_PA5OD_DISABLE | FUSE_BOOTUP_FAST);
  return 0;
}


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on April 30, 2021, 03:17:32 pm
I think I found something strange regarding the "set1 M.n" instruction on the PDK13 (e.g. the  PMS150c). See the following example code:


.area OSEG (OVR,DATA)
tmp: .ds 22
var: .ds 1  ; 0x16

.area CSEG (CODE,ABS)
.org 0x0000
init:
   SET1   var, #3


Assemble it and disassemble it again:


sdaspdk13 -o test.rel test.asm
sdldpdk -ni test.ihx test.rel
dispdk 2A16 test.ihx

0x0000:   0x0376    SET1 [0x06].3


Notice that set1 should operate on memory location 0x16, but the disassembler thinks it works on address 0x06.

It gets even stranger when analyzing the code with ucsim (since i couldn't find a command to list instructions, setting the program counter to 0 shows the first instruction):


spdk -t PDK13 test.ihx
0>pc 0

 ? 0x000 0376 set0  54, #3


It thinks, it's set0 on 0x36!

Looking at the documentation (https://free-pdk.github.io/instruction-sets/PDK13), it looks like there was an error creating the table: the last two columns (constant and memaddr) are flipped in the header/body of the table (see attached screenshot). So which one is right?

Looking at the documentation at least made me realize that set1 M.n can only work on the first 16 SRAM-addresses. Given that, I think the assembler (or linker) should give an error here. Or is there something else going on?

edited to add: the 4-bit limitation is not mentioned in the datasheet, afaict.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on April 30, 2021, 04:36:59 pm
Also, ucsim seems to not handle 't0sn IO.n'? the first example sets flag.zero, the second example clears it (this seems to work, looking at the Flag= output of ucsim). But in both cases ucsim continues execution with the next instruction (the goto)?!

Code: [Select]
mov a, #0
and a, #1
t0sn f, z
goto foo
        Flag= 0x01(  1)
         ? 0x040 0c00 t0sn  [0], #0
        Flag= 0x01(  1)
         ? 0x041 1845 goto  #69
mov a, #1
and a, #1
t0sn f, z
goto foo
        Flag= 0x04(  4)
         ? 0x040 0c00 t0sn  [0], #0
        Flag= 0x04(  4) 
         ? 0x041 1845 goto  #69
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on April 30, 2021, 10:29:55 pm

Looking at the documentation (https://free-pdk.github.io/instruction-sets/PDK13), it looks like there was an error creating the table: the last two columns (constant and memaddr) are flipped in the header/body of the table (see attached screenshot). So which one is right?


The header is wrong. Should read |c|4-bit MEM addr|


Looking at the documentation at least made me realize that set1 M.n can only work on the first 16 SRAM-addresses. Given that, I think the assembler (or linker) should give an error here. Or is there something else going on?

edited to add: the 4-bit limitation is not mentioned in the datasheet, afaict.

Documentation says first 16 SRAM addresses can be used which translates to 4 bit for the address (4 bit can encode 16 addresses).
So why do you think "the 4-bit limitation is not mentioned in the datasheet, afaict."?

I agree that the assembler could bring up a warning / error in this case (you can create a ticket for sdcc developers).

Everything is working correct, just a missing warning.

SDCC (the c compiler) does not use this special instructions (since it can not predict if a variable will end up in the desired space).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 01, 2021, 07:56:36 am
Also, ucsim seems to not handle 't0sn IO.n'? the first example sets flag.zero, the second example clears it (this seems to work, looking at the Flag= output of ucsim). But in both cases ucsim continues execution with the next instruction (the goto)?!

Code: [Select]
mov a, #0
and a, #1
t0sn f, z
goto foo
        Flag= 0x01(  1)
         ? 0x040 0c00 t0sn  [0], #0
        Flag= 0x01(  1)
         ? 0x041 1845 goto  #69
mov a, #1
and a, #1
t0sn f, z
goto foo
        Flag= 0x04(  4)
         ? 0x040 0c00 t0sn  [0], #0
        Flag= 0x04(  4) 
         ? 0x041 1845 goto  #69

Are you sure the goto instruction is actually executed in both cases?

Like the real IC all of the ...SN (skip next) instructions, the next instruction is fetched regardless of the "skip" state. Just execution of the instruction will be controlled by the SN.

So you see the PC always "walk" over the next instruction, it just will be ignored or executed based on the "skip" state.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on May 01, 2021, 12:32:28 pm
Thank you for fixing the table, JS!

Quote
Documentation says first 16 SRAM addresses can be used which translates to 4 bit for the address (4 bit can encode 16 addresses).

Well, I can't seem to find it (looking at the PMS150c v1.08 datasheet), but I guess I just needed a place to vent, since I wasted too much time on this quirk.

Quote
I agree that the assembler could bring up a warning / error in this case (you can create a ticket for sdcc developers).

'll do!

Quote
Are you sure the goto instruction is actually executed in both cases?

yes, the simulator follows the jump and continues execution at the same place.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 02, 2021, 06:40:44 pm
I'm very close to finish support for PFC154.

Unfortunately it turned out, that this and some other new ICs require VDD >6.2 V for writing:

PFC154: VDD write hv: 7.8V
PMS150G: VDD write hv: 7.8V
...

While PMS150G seems to write reliable with the maximum easypdk programmer can produce (6.2V), writing PFC154 needs >7.2V to reliably write all bits. Even multiple writes could not overcome this issue.

==> So it seems we need to do a hardware mod on the programmer in order to support those ICs.

The only change needed is to swap the resistor R6 from 20k to 6.8k.

I will add an auto detection so existing programmer can be used as is. Only if you want to write the specific ICs you need to do the change.

JS

EDIT: PFC154 support is done (-> development branch, requires new firmware build for programmer and hardware mod to get VDD to 7.0V => change R6 to 6.8k)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on May 03, 2021, 04:17:30 am
My project is done, btw: https://gir.st/chiptunes.html | https://git.gir.st/Chiptunes-pms150c.git

It plays 16 minutes of chiptune music when it's plugged in and requires no external components (well, except a coin cell).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on May 05, 2021, 09:27:58 am
Attached file "reload.zip"
It's io loop.

picture 1.  don't "A5A5A5A4" key

picture 2.  have "A5A5A5A4" magic key

PA3, P4, P5 connect to ardunio

It's generate "A5A5A5A4"
PA6 is PMG150C or PMG150G  clock source.
When  PA6 clock stop, then PA0, PA7  stop.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 05, 2021, 12:45:23 pm
Attached file "reload.zip"
It's io loop.

Not sure what you want to show here. When you use programing startup sequence (VPP first, then VDD, then PREAMBLE "A5A5A5A" and then COMMAND "4) your code will NOT be executed.
So why do you present your "reload.asm" program here?

picture 1.  don't "A5A5A5A4" key
picture 2.  have "A5A5A5A4" magic key
PA3, P4, P5 connect to ardunio
It's generate "A5A5A5A4"
PA6 is PMG150C or PMG150G  clock source.
When  PA6 clock stop, then PA0, PA7  stop.

Like I wrote before CMD4 seems to be some special new programming command with unknown behavior.

In case you do NOT send the PREAMBLE + CMD within a specific time then IC will boot normally. This might be what you observe here...

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: homeworkboy on May 06, 2021, 12:51:31 am
Hi Js:
I want to say,Padauk to have such a function?
Or  Padauk can read the protected code

Hong
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on May 06, 2021, 04:57:21 am
My project is done, btw: https://gir.st/chiptunes.html | https://git.gir.st/Chiptunes-pms150c.git

It plays 16 minutes of chiptune music when it's plugged in and requires no external components (well, except a coin cell).

Wow, this is really great! Love everything about it - the flexboard solution, actually thinking through the signal path for audio (many designs just drop the PWM stream somwhere :) ), plug in detection. Congrats!

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on May 11, 2021, 01:04:30 am
Hi js

A quick question regarding the 16 bit timer.
In mini-c there's an instruction that called stt16. Which can set the value of T16 counter with one single 16 bit value(word). Is it possible to do so in Free PDK?

Thank you
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on May 11, 2021, 10:34:58 am
Hi js

A quick question regarding the 16 bit timer.
In mini-c there's an instruction that called stt16. Which can set the value of T16 counter with one single 16 bit value(word). Is it possible to do so in Free PDK?

Thank you

stt16 is an assembler instruction.

SDCC supports the functionality to some degree via __sfr16. If the support in SDCC isn't sufficient for you, you can use the stt16 assembler instruction, e.g. via inline asm in a C function, or by just writing some code in assembler and then linking it with the rest of your program.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on May 12, 2021, 02:40:54 am
__sfr16? Is that a macro or sth?
An example will be greatly appreciated.

Thank you
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 12, 2021, 08:49:06 am
__sfr16? Is that a macro or sth?
An example will be greatly appreciated.

Thank you

Hi,

if you have a look in "https://github.com/free-pdk/easy-pdk-programmer-software/blob/master/Examples/src/easypdk/pfs154.h" for example you can see:

...
__sfr16          _t16c;
...
#define T16C      _t16c
...

This means you can access the T16 counter value in C code like this:

T16C = 0;

However code generation for this from sdcc-pdk compiler is not fully supported. There was a discussion in this thread for alternatives:

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3262818/#msg3262818 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3262818/#msg3262818)

however using the virtual 'p' register was not a good choice:

https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3264414/#msg3264414 (https://www.eevblog.com/forum/blog/eevblog-1144-padauk-programmer-reverse-engineering/msg3264414/#msg3264414)

and the conclusion from "pacmancoder" :

So for now, the most usable way of using ldt16/stt16 is to make sdcc to place uint16_t variables to the word aligned address by placing as the first items in the first translation unit as JS suggested, or by introducing the additional single byte variables before ldt16/stt16 operand variables if their address is non-aligned.

is the way to go.

Here a small example how it could work:

#define _STRINGIFY(x) #x
#define _STR_VAR(x) "_"_STRINGIFY(x)

uint16_t t16c_tmp;

#define __ldt16(var) __asm__( \
    "ldt16 _t16c_tmp\n"\
    "mov a, _t16c_tmp\n"\
    "mov "_STR_VAR(var)", a\n"\
    "mov a, _t16c_tmp+1\n"\
    "mov "_STR_VAR(var)"+1, a\n"\
  );

#define __stt16(var) __asm__( \
    "mov a, "_STR_VAR(var)"\n"\
    "mov _t16c_tmp, a\n"\
    "mov a, "_STR_VAR(var)"+1\n"\
    "mov _t16c_tmp+1, a\n"\
    "stt16 _t16c_tmp\n"
  );

...


in your code you could now do:

uint16_t myT16val;

__ldt16(myT16val); //load IC T16C register into myT16val

myT16val = 0x1234;

__stt16(myT16val); //store myT16val into IC T16C register



JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on May 12, 2021, 02:19:30 pm
Hi JS

Thanks for the code example! however, the code doesn't work as expected. No matter which value I wrote during the T16 interrupt, the frequency stayed the same.
T16C does work and can modify the frequency. However, it only worked with 8 bit values(as you said, it's not implemented. They should really implement the 16bit part of it. Since in Mini-C you can just do "stt16 a16BitValue;" and everything works)
I also saw this error during the compilation.
?ASlink-Warning-Invalid address for instruction
Code: [Select]
-------------- Build: Release in PWMBell154 (compiler: Small Device C Compiler)---------------

sdcc.exe -mpdk14  --opt-code-size  -std=c11   -IC:\Software\FreePDK\include -IC:\Software\sdcc\include -c main.c -o obj\Release\main.rel
sdcc.exe -LC:\Software\sdcc\lib -o bin\Release\PWMBell154.ihx -mpdk14  --opt-code-size  -std=c11    -lpdk14 obj\Release\main.rel
at 1: warning 118: option '-s' no longer supported  'use --code-loc instead'
?ASlink-Warning-Invalid address for instruction
         file              module            area              offset
  Refby  obj\Release\ma    main              CODE                   000078
  Defin  obj\Release\ma    main              DATA                   000007
at 1: warning 118: option '-s' no longer supported  'use --code-loc instead'
Process terminated with status 1 (0 minute(s), 0 second(s))
0 error(s), 1 warning(s) (0 minute(s), 0 second(s))
 
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 12, 2021, 06:46:23 pm
Hi JS

Thanks for the code example! however, the code doesn't work as expected. No matter which value I wrote during the T16 interrupt, the frequency stayed the same.
T16C does work and can modify the frequency. However, it only worked with 8 bit values(as you said, it's not implemented. They should really implement the 16bit part of it. Since in Mini-C you can just do "stt16 a16BitValue;" and everything works)
I also saw this error during the compilation.
?ASlink-Warning-Invalid address for instruction
Code: [Select]
-------------- Build: Release in PWMBell154 (compiler: Small Device C Compiler)---------------

sdcc.exe -mpdk14  --opt-code-size  -std=c11   -IC:\Software\FreePDK\include -IC:\Software\sdcc\include -c main.c -o obj\Release\main.rel
sdcc.exe -LC:\Software\sdcc\lib -o bin\Release\PWMBell154.ihx -mpdk14  --opt-code-size  -std=c11    -lpdk14 obj\Release\main.rel
at 1: warning 118: option '-s' no longer supported  'use --code-loc instead'
?ASlink-Warning-Invalid address for instruction
         file              module            area              offset
  Refby  obj\Release\ma    main              CODE                   000078
  Defin  obj\Release\ma    main              DATA                   000007
at 1: warning 118: option '-s' no longer supported  'use --code-loc instead'
Process terminated with status 1 (0 minute(s), 0 second(s))
0 error(s), 1 warning(s) (0 minute(s), 0 second(s))
 
The warning suggests that you did not place the temp variable "uint16_t t16c_tmp;" at an even address (word alignment is needed for 16 bit access).
Maybe you defined some other variables (e.g. 1, 3, 5, 7, ... bytes) before that.
To make sure all your 16 bit variables are word aligned you can define them at the start of your main c code file, just before defining other variables.
In order to find the real cause it would be helpful to post a complete demo project / source code showing the problem.

BTW: Not sure why you want to write to the counter register of timer16 in order to change it's frequency. T16 frequency is specified via the scaler / pre scaler. In case you need finer control then you could use TM2 or TM3 with their "bound" register.
You also can use the interrupt (of a faster) timer to count a variable which then only triggers something when it reaches a specific value.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 14, 2021, 10:33:56 am
Hi,

we now have support for PFC232. A flash based "Multi-Core" IC (in development branch).  8) 8) 8)

I added a dual core example hello world:
* core 1 sends out the "Hello World!" string
* core 2 detects pin changes on incoming serial port and sets a flag
* when core1 sees the flag it will clear it and output a '2' (hello from core 2)

When you run the 2core hello world directly in easy pdk programmer it will capture and output the "Hello World!" and when you press a key on the host computer (which causes serial data to be sent, which causes pin changes detected by core2) you will get some '2' outputs:

./easypdkprog -n PFC232 write Examples/src/build/helloworld_2cores_pfc232.ihx -v
Searching programmer... found: /dev/tty.usbmodem1234567855AA1
FREE-PDK EASY PROG - HW:1.2 SW:1.3 PROTO:1.4 (1.3-40-g98c7c8d-dirty)
HWVAR:0 HWMOD:1
Erasing IC... done.
Blank check IC... done.
Writing IC (321 words)... done.
Verifiying IC... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 5.00V ... calibration result: 7949466Hz (0x70)  done.

./easypdkprog start
Running IC (5.00V)... IC started, press [Esc] to stop.
Connected @168421 baud
Press a key on the host computer to send some bits, core2 will detect this and core1 will output a '2' for every 1 bit
Hello World!
Hello World!
222222222222222222Hello World!
222222222222222222222Hello World!
Hello World!

IC stopped


==> BE AWARE: SDCC PDK compiler does not support code generation for parallel execution of functions. Our best chance is to use SDCC C code for core1 and write assembly code for all additional cores.

JS

P.S. Calibration seems a bit wrong. That's why it shows so high baud rate. I will have look at it.

Edit: Interesting... The 7 cycle calibration loop seems to take 10 cycles on this IC.
Where are the 3 extra cycles coming from ? ? ? The IC runs in "single core" mode during calibration.

Calibration loop is like this:

LOOP:
  SET1 IO(0x10).3  (PA.3)
  MOV IO(0x0B), A  (IHRCR)
  T0SN IO(0x10).4  (PA.4)
  ADD A, 0x01
  SET0 IO(0x10).3
  GOTO LOOP


Maybe it is from context switching between cores, even that FPPEN only activated core 1 during calibration?
When setting the fuse bit to use only 1 core then the above loop will take the exact 7 cycles.  ???

Looks like PDK IDE + WRITER also sets the (single core) fuse before calibration. I wonder what this fuse actually means...


EDIT2: During analyzing the PDK IDE stub inserted for PFC232 IC calibration I found 2 new undocumented instructions in 14 bit instructions set.
Most likely LDTABL and LDTABH  8) 8) 8) (like in 15 bit instruction set).

0   0   0   0   0   1   0   (7-bit MEM addr)  0    LDTABL M  :  A ← LowByte@CodeMem(M)  (last bit of M set to 0, M must be word aligned)

0   0   0   0   0   1   0   (7-bit MEM addr)  1    LDTABH M  :  A ← HighByte@CodeMem(M) (last bit of M set to 1, M must be word aligned)

8)  Very useful for lookup tables in code mem...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: kaweksl on May 15, 2021, 11:42:32 am
Hi,

we now have support for PFC232. A flash based "Multi-Core" IC (in development branch).  8) 8) 8)


Thanks for that.

Can you give some more details about that R6 mod witch is required for that to work ?

EDIT:

Ok, i found info that R6 have to be changed to 20k

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 16, 2021, 02:26:04 am
Hi,

we now have support for PFC232. A flash based "Multi-Core" IC (in development branch).  8) 8) 8)


Thanks for that.

Can you give some more details about that R6 mod witch is required for that to work ?

EDIT:

Ok, i found info that R6 have to be changed to 20k

In fact R6 needs to be changed from 20k to 6.2k.

However, I was able to capture a "limited voltage" write (VDD max used 5V), which I will try to implement. Then no hardware mod is needed for this IC.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on May 20, 2021, 05:45:27 am
Hello

I just read that the PFC232 can now also be used. Could anyone tell me, where you can buy this uC? I searched LCSC for it, but it seems the do not sell it right now.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on May 20, 2021, 07:39:38 am
And there is another question I have. For experimenting I use the PFS154, a breadboard and my lab bench power supply. It seems the uC has always problems and does not function as expected, if I enable the power output of my power supply. I have to apply power first and then put the uC on the breadboard or disconnect the power cable and connect it again.
I looked at the power on behavior. There are no peaks, only the loading curve of the output capacitors can be seen.
What could be the problem?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 20, 2021, 12:47:16 pm
And there is another question I have. For experimenting I use the PFS154, a breadboard and my lab bench power supply. It seems the uC has always problems and does not function as expected, if I enable the power output of my power supply. I have to apply power first and then put the uC on the breadboard or disconnect the power cable and connect it again.
I looked at the power on behavior. There are no peaks, only the loading curve of the output capacitors can be seen.
What could be the problem?

Make sure you set setup LVR (Low Voltage Reset) in case you use a sysclock >= 2MHz.
In case you set a higher sysclock and your power supply is just ramping up (supplying like 2V) the IC starts up (using ILRC) but then locks up when switching to the higher clock (e.g. IHRC/2).

There was a discussion about this, some "pages" ago in this thread.

The examples which come with easy pdk programmer software include automatic setup of LVR based on clock frequency. Have a look at the Examples/src/easypdk headers, e.g.:
https://github.com/free-pdk/easy-pdk-programmer-software/blob/development/Examples/src/easypdk/pfs154.h
...
#define EASY_PDK_INIT_SYSCLOCK_8MHZ()       {_misclvr=MISCLVR_3V5;_clkmd=CLKMD_ENABLE_ILRC|CLKMD_ENABLE_IHRC|CLKMD_IHRC_DIV2;}

...
JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on May 20, 2021, 04:54:58 pm
Okay, thank you. I think that is the case. I use the uC at 8MHz
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on May 25, 2021, 12:59:23 pm
I added a new example "Noiseplug" to the easy-pdk-showcase-projects: https://github.com/free-pdk/easy-pdk-showcase-projects (https://github.com/free-pdk/easy-pdk-showcase-projects)

* Noiseplug is a chiptune player for ATTiny9 created by "dojoe/shack" presented @evoke2012:
* Pouet: https://www.pouet.net/prod.php?which=59694 (https://www.pouet.net/prod.php?which=59694)
* Source: https://github.com/dojoe/noiseplug (https://github.com/dojoe/noiseplug)

Out of curiosity I wanted to see how well assembly code from ATtiny can be ported to PADAUK.
It turned out, very well (unless you use any peripherals like UART or high speed clock (20MHz) from ATtiny it is possible to port assembly programs almost 1:1).

Just for fun I also added a tiny PFS154 emulator which loads an .IHX hex file, interprets the PDK14 instructions and sends the PWM output of TM2 to the host computer's sound device (your host computer needs to run at least @150MHz).
=> https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation (https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation)

JS

P.S. @gir:
I modified your bsv makefile to compile for pdk14 and changed 2 things in my emulator (512 instead of 256 syclocks, trigger TM16 int (0x04) instead of TM2 int) and it played the tune very well.
I think you can easily load noiseplug on your hardware (you only need to change the PWM output to use PA4)

---
Video of original ATTiny noiseplug (at demo party EVOKE 2012):

https://www.youtube.com/watch?v=AZpfHiwQf-s (https://www.youtube.com/watch?v=AZpfHiwQf-s)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: gir on May 29, 2021, 10:57:05 am
P.S. @gir:
I modified your bsv makefile to compile for pdk14 and changed 2 things in my emulator (512 instead of 256 syclocks, trigger TM16 int (0x04) instead of TM2 int) and it played the tune very well.
I think you can easily load noiseplug on your hardware (you only need to change the PWM output to use PA4)

nice to see that my assembly was portable enough (i think i did use some magic numbers for bits-in-registers here and there...). and great job on your noiseplug port --  i'm definitely going to try that out!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 04, 2021, 03:54:41 pm
I stumbled over a comment on github (all in chinese) which is asking if we want to research the PFC886 together...

There is a repository with source here: https://github.com/stm8stm8stm8/pfc886/blob/main/pwm08b.C (https://github.com/stm8stm8stm8/pfc886/blob/main/pwm08b.C)

Which according to the comment contains code for the "PFC886" IC which is also labeled "MF520".

After following the bread crumbs it turns out that PADAUK offers a special IC for brushless DC motors called the MF520:

http://www.padauk.com.tw/en/product/show.aspx?num=138&kind=44 (http://www.padauk.com.tw/en/product/show.aspx?num=138&kind=44)

In fact this seems to be an 8 core PADAUK with flash support  :) 8)

EDIT:After some more digging I found a video of the "making of" the above source code:

https://www.bilibili.com/video/av712877080/ (https://www.bilibili.com/video/av712877080/)

The video contains some captures of the PFC886 datasheet (again all in chinese :-) )

EDIT2: In the video I was able to see that this IC has 512 byte of RAM  :o

Interesting....
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 10, 2021, 09:06:05 am
hello,goodmorning. video is:
https://video.kuaishou.com/short-video/3xkzb3zuyvg3vku?authorId=3xmydwifg7bk3yk&streamSource=profile&area=profilexxnull
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 10, 2021, 09:23:39 am
/***************************************PFC886+MF520PWM**********************************************/
/***************************************QQ:774145445*************************************************/
/****************************************快手:共同学习STM8*******************************************/
/****************************************20210423****************************************************/
//                     _________   _________
//              PWM2L-|1 pa2    \_/   pa1 20|-PWM2H
//              PWM1L-|2 pa3          pa0 19|-PWM1H
//              pwm0L-|3 pa4          pa7 18|-pwm0H
//                    |4 pa5          pa6 17|-led_1
//         与gnd相连|-|5 nc            nc 16|-|与vdd相连
//                  |-|6 gnd          vdd 15|-|
//                k_1-|7 pb0          pb7 14|-led_2
//                k_2-|8 pb1          pb6 13|-led_3
//                k_3-|9 pb2          pb5 12|-led_4
//                k_4-|10_pb3_________pb4_11|-led_5
#include   "extern.h"
/****************************************************************************************************/
k_1         bit      pb.0;
k_2         bit      pb.1;
k_3         bit      pb.2;
k_4         bit      pb.3;
led_1      bit      pa.6;
led_2      bit      pb.7;
led_3      bit      pb.6;
led_4      bit      pb.5;
led_5      bit      pb.4;
/****************************************************************************************************/
void      zhengxianbo();      //正弦波
void      fuzhi();         //赋值
void      anjian();         //按键
void      yanshi();         //延时
/****************************************************************************************************/
word      a1,b1,c1;
word      yanshi_a1;
/****************************************************************************************************/
void   FPPA0 (void)
{
.ADJUST_IC   SYSCLK=IHRC/4      //   SYSCLK=IHRC/4
pmode      31;         ///8/8/8/8/8/8/8/8带宽共享
fppen   =   0xFF;      //8核全开有8个核心可以分时全部运行,可以分别干8件事8核真爽!
/****************************************************************************************************/
$      led_1      out,low;
$      k_1         in,pull;
$      k_2         in,pull;
/****************************************************************************************************/      //pwm配置
//f----------------0 f----------------0 f----------------0 f----------------0(word,int)
//f----------------0 f----------------0 f----------------0    //12位PWM0,1,2(左对齐)
// ↑上限(pwmcub)    ↑占空比(pwmdt)    |--死区(pwmdz)---|

//上限pwmcub=0xfff0,死区pwmdz=0xff,
//pwm0dtl(先写)pwm0dth,pwm1dtl(先写)pwm1dth,pwm2dtl(先写)pwm2dth,

//最大0xf010,        pwm_h=1+死区,    pwm_l=0,
//最小0x000,0x0010,  pwm_h=0,         pwm_l=1,
//PWM最大0x0fff-死区 =0xf000,
//PWM最小0x0000+2    =0x0020,
//pwm最大值取0xf000-0xff    =<0xef00高脉冲4us
//pwm最小值取0x0020+0xff    =>0x00ff高脉冲4us
/*
a1=0xf010;fuzhi();yanshi();
//a1=0x0000;fuzhi();yanshi();
a1=0x0010;fuzhi();yanshi();
a1=0xf000;fuzhi();yanshi();
a1=0x0020;fuzhi();yanshi();*/
/****************************************************************************************************/
$      pwmgc      enable,updown,reset;
$      pwmgm      protection_enable,ihrc,/4;
//pwmgc      =0b1_0_1_1_0000;      //PWMG控制寄存器位7,停用启用位6,输出状态位5,中心排列模式位4,PWM计数器清零

//pwmgm      =0b0_0_1_0_10_10;      //PWMG分频寄存器位7,上臂反极性位6,下臂反极性位5,臂保护位4,臂保护模式位32,PWM时钟源位10,PWM分频
//pwmgm      =0b0_0_1_0_10_11;      //PWMG分频寄存器

pwmgc1      =0b1_11_0_01_10;      //PWMG控制寄存器1位7,互补发生器位65,三相电机位4,读零位32,PWM5.PWM+位10,PWM4.PWM-

pwmgc2      =0b01_10_01_10;      //PWMG控制寄存器2位76,PWM3.PWM+位54,PWM2.PWM-位32,PWM1.PWM+位10,PWM0.PWM-

pwmcubl      =0b1111_0000;      //pwm上限寄存器l
pwmcubh      =0b1111_1111;      //pwm上限寄存器h

//pwmdz      =0b1111_0000;      //死区寄存器
pwmdz      =0b1111_1111;      //死区寄存器//*注意死区占上臂时间需要扣除

//pwm0dtl      =0b1111_0000;      //pwm0占空比低位寄存器//先写低位
//pwm0dth      =0b1111_1111;      //pwm0占空比高位寄存器

//pwm1dtl      =0b0000_0000;      //pwm1占空比低位寄存器//先写低位
//pwm1dth      =0b1000_0000;      //pwm1占空比高位寄存器

//pwm2dtl      =0b1111_0000;      //pwm2占空比低位寄存器//先写低位
//pwm2dth      =0b0000_0000;      //pwm2占空比高位寄存器

/****************************************************************************************************/
while (1)
{
if(led_1){led_1=0;}   else{led_1=1;}
.delay   10000;
}
}
/****************************************************************************************************/
void   FPPA1 (void)
{
while(1)
{
zhengxianbo();      //正弦波

}
}
/****************************************************************************************************/
void   FPPA2 (void)
{
yanshi_a1      =2000;
while(1)
{
anjian();
}
}
/****************************************************************************************************/
void   FPPA3 (void)
{
   goto   $;
}
/****************************************************************************************************/
void   FPPA4 (void)
{
   goto   $;
}
/****************************************************************************************************/
void   FPPA5 (void)
{
   goto   $;
}
/****************************************************************************************************/
void   FPPA6 (void)
{
   goto   $;
}
/****************************************************************************************************/
void   FPPA7 (void)
{
   goto   $;
}
/****************************************************************************************************/
/*
void   Interrupt (void)
{
   pushaf;

   if (Intrq.T16)
   {   //   T16 Trig
      //   User can add code
      Intrq.T16   =   0;
      //...
   }

   popaf;
}
*/
/****************************************************************************************************///使用spwm_calc生成幅值61184,周内点数48(52),对称,半波模式,
void      zhengxianbo()      //正弦波
{
while(1)
{

 a1 =0x795D; b1 =0xE438; c1 =0x25D3; fuzhi(); yanshi();
// a1 =0x84C8; b1 =0xDF65; c1 =0x1DD4; fuzhi(); yanshi();
 a1 =0x9010; b1 =0xD998; c1 =0x16A9; fuzhi(); yanshi();
// a1 =0x9B1C; b1 =0xD2DD; c1 =0x1063; fuzhi(); yanshi();
 a1 =0xA5D0; b1 =0xCB46; c1 =0x0B11; fuzhi(); yanshi();
// a1 =0xB012; b1 =0xC2E4; c1 =0x06C0; fuzhi(); yanshi();
 a1 =0xB9CC; b1 =0xB9CC; c1 =0x037A; fuzhi(); yanshi();
// a1 =0xC2E4; b1 =0xB012; c1 =0x06C0; fuzhi(); yanshi();
 a1 =0xCB46; b1 =0xA5D0; c1 =0x0B11; fuzhi(); yanshi();
// a1 =0xD2DD; b1 =0x9B1C; c1 =0x1063; fuzhi(); yanshi();
 a1 =0xD998; b1 =0x9010; c1 =0x16A9; fuzhi(); yanshi();
// a1 =0xDF65; b1 =0x84C8; c1 =0x1DD4; fuzhi(); yanshi();
 a1 =0xE438; b1 =0x795D; c1 =0x25D3; fuzhi(); yanshi();
// a1 =0xE805; b1 =0x6DEB; c1 =0x2E92; fuzhi(); yanshi();
 a1 =0xEAC2; b1 =0x628E; c1 =0x37FE; fuzhi(); yanshi();
// a1 =0xEC6A; b1 =0x5761; c1 =0x41FF; fuzhi(); yanshi();
 a1 =0xECF7; b1 =0x4C7E; c1 =0x4C7E; fuzhi(); yanshi();
// a1 =0xEC6A; b1 =0x41FF; c1 =0x5761; fuzhi(); yanshi();
 a1 =0xEAC2; b1 =0x37FE; c1 =0x628E; fuzhi(); yanshi();
// a1 =0xE805; b1 =0x2E92; c1 =0x6DEB; fuzhi(); yanshi();



 a1 =0xE438; b1 =0x25D3; c1 =0x795D; fuzhi(); yanshi();
// a1 =0xDF65; b1 =0x1DD4; c1 =0x84C8; fuzhi(); yanshi();
 a1 =0xD998; b1 =0x16A9; c1 =0x9010; fuzhi(); yanshi();
// a1 =0xD2DD; b1 =0x1063; c1 =0x9B1C; fuzhi(); yanshi();
 a1 =0xCB46; b1 =0x0B11; c1 =0xA5D0; fuzhi(); yanshi();
// a1 =0xC2E4; b1 =0x06C0; c1 =0xB012; fuzhi(); yanshi();
 a1 =0xB9CC; b1 =0x037A; c1 =0xB9CC; fuzhi(); yanshi();
// a1 =0xB012; b1 =0x06C0; c1 =0xC2E4; fuzhi(); yanshi();
 a1 =0xA5D0; b1 =0x0B11; c1 =0xCB46; fuzhi(); yanshi();
// a1 =0x9B1C; b1 =0x1063; c1 =0xD2DD; fuzhi(); yanshi();
 a1 =0x9010; b1 =0x16A9; c1 =0xD998; fuzhi(); yanshi();
// a1 =0x84C8; b1 =0x1DD4; c1 =0xDF65; fuzhi(); yanshi();
 a1 =0x795D; b1 =0x25D3; c1 =0xE438; fuzhi(); yanshi();
// a1 =0x6DEB; b1 =0x2E92; c1 =0xE805; fuzhi(); yanshi();
 a1 =0x628E; b1 =0x37FE; c1 =0xEAC2; fuzhi(); yanshi();
// a1 =0x5761; b1 =0x41FF; c1 =0xEC6A; fuzhi(); yanshi();
 a1 =0x4C7E; b1 =0x4C7E; c1 =0xECF7; fuzhi(); yanshi();
// a1 =0x41FF; b1 =0x5761; c1 =0xEC6A; fuzhi(); yanshi();
 a1 =0x37FE; b1 =0x628E; c1 =0xEAC2; fuzhi(); yanshi();
// a1 =0x2E92; b1 =0x6DEB; c1 =0xE805; fuzhi(); yanshi();


 a1 =0x25D3; b1 =0x795D; c1 =0xE438; fuzhi(); yanshi();
// a1 =0x1DD4; b1 =0x84C8; c1 =0xDF65; fuzhi(); yanshi();
 a1 =0x16A9; b1 =0x9010; c1 =0xD998; fuzhi(); yanshi();
// a1 =0x1063; b1 =0x9B1C; c1 =0xD2DD; fuzhi(); yanshi();
 a1 =0x0B11; b1 =0xA5D0; c1 =0xCB46; fuzhi(); yanshi();
// a1 =0x06C0; b1 =0xB012; c1 =0xC2E4; fuzhi(); yanshi();
 a1 =0x037A; b1 =0xB9CC; c1 =0xB9CC; fuzhi(); yanshi();
// a1 =0x0B11; b1 =0xCB46; c1 =0xA5D0; fuzhi(); yanshi();
 a1 =0x1063; b1 =0xD2DD; c1 =0x9B1C; fuzhi(); yanshi();
// a1 =0x16A9; b1 =0xD998; c1 =0x9010; fuzhi(); yanshi();
 a1 =0x1DD4; b1 =0xDF65; c1 =0x84C8; fuzhi(); yanshi();
// a1 =0x25D3; b1 =0xE438; c1 =0x795D; fuzhi(); yanshi();
 a1 =0x2E92; b1 =0xE805; c1 =0x6DEB; fuzhi(); yanshi();
// a1 =0x37FE; b1 =0xEAC2; c1 =0x628E; fuzhi(); yanshi();
 a1 =0x41FF; b1 =0xEC6A; c1 =0x5761; fuzhi(); yanshi();
// a1 =0x4C7E; b1 =0xECF7; c1 =0x4C7E; fuzhi(); yanshi();
 a1 =0x5761; b1 =0xEC6A; c1 =0x41FF; fuzhi(); yanshi();
// a1 =0x628E; b1 =0xEAC2; c1 =0x37FE; fuzhi(); yanshi();
 a1 =0x6DEB; b1 =0xE805; c1 =0x2E92; fuzhi(); yanshi();


}
}
/****************************************************************************************************/
void      fuzhi()         //赋值
{
pwm0dtl      =a1 $0;      //先写
pwm0dth      =a1 $1;

pwm1dtl      =b1 $0;
pwm1dth      =b1 $1;

pwm2dtl      =c1 $0;
pwm2dth      =c1 $1;
}
/****************************************************************************************************/
void      yanshi()         //延时
{
word      yanshi_b1;
yanshi_b1      =yanshi_a1;
while(yanshi_b1--){}
//while(k_1){.delay 1000;if(k_2==0){a1--;fuzhi();}}      //定在这
//while(!k_1){.delay 1000;}
}
/****************************************************************************************************/
void      anjian()         //按键
{
if(k_1==0)
{
yanshi_a1++;
.delay 800;
}
if(k_2==0)
{
yanshi_a1--;
.delay 800;
}
}
/****************************************************************************************************/
/****************************************************************************************************/
/****************************************************************************************************/
/****************************************************************************************************/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on June 10, 2021, 09:24:38 am
In case you didn't know, Suzhiming is that stm8stm8stm8 user on github.
A while ago I introduced FreePDK to him and seems like he's very interested in this project.
He is a Mini-C expert and he's a commercial MCU solution developer.

Btw: these variable names are in Chinese pinyin so they are only make sense to Chinese like us...  :-// but I am helping him with his English.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 10, 2021, 09:30:40 am
i 'm sorry very funny
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: NickE on June 10, 2021, 06:46:18 pm
This chip is also out of stock at LCSC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 11, 2021, 01:30:59 am
样片的话好办,工程的话还得分型号价格十倍(up*10)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 11, 2021, 01:34:54 am
up mew touch mcu flash :pfc161




/*****************pfc161+tm1651********************/
/******************20210608************************/
/****************qq:774145445**********************/
/****************快手:共同学习stm8*****************/
/**************************************************/
//               _______    ______
//          dio-|1 pb7  \_/  pb010|-clk
//              |2 vdd       gnd 9|
//        cs-||-|3 pa7       pa0 8|-hong
//          tk8-|4 pa6       pa4 7|-lv
//          tk9-|5_pa5_______pa3_6|-lan
//       5v
//  pb0--clk
//  pb7--dio
//       gnd
/**************************************************/
#include   "extern.h"
tm1651_clk      bit      pb.0;
tm1651_dio      bit      pb.7;
/**************************************************/
byte      tm1651_a1;
/**************************************************/
void      tm1651_yanshi();      //延时
void      tm1651_start();         //起始信号
void      tm1651_data();         //数据
void      tm1651_ack();         //应答
void      tm1651_stop();         //结束
/**************************************************/
void   FPPA0 (void)
{
.ADJUST_IC   SYSCLK=IHRC/4      //   SYSCLK=IHRC/4
$      tm1651_clk      out,high;      //输出,高
$      tm1651_dio      out,high;
/**************************************************/


tm1651_yanshi();
while (1)
{
tm1651_start();
tm1651_a1   =0b0100_0000;   tm1651_data();      //写数据到显示寄存器,自动地址增加
tm1651_stop();
tm1651_start();
tm1651_a1   =0b1100_0000;   tm1651_data();      //设置地址00H
tm1651_a1   =0b1111_1111;   tm1651_data();
tm1651_a1   =0b0000_0000;   tm1651_data();
tm1651_a1   =0b0000_1111;   tm1651_data();
tm1651_a1   =0b1111_0000;   tm1651_data();
tm1651_stop();
tm1651_start();
tm1651_a1   =0b1000_1011;   tm1651_data();      //显示开,10/16
tm1651_stop();

//while(1){}
}
}

/**************************************************/
void      tm1651_yanshi()      //延时
{
.delay 100;
}
/**************************************************/
void      tm1651_start()         //起始信号
{
tm1651_clk   =1;   tm1651_dio   =1;   tm1651_yanshi();
tm1651_clk   =1;   tm1651_dio   =0;   tm1651_yanshi();

}
/**************************************************/
void      tm1651_data()         //数据
{

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.0){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.1){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.2){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.3){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.4){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.5){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.6){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.7){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();



tm1651_ack();

}

/**************************************************/
void      tm1651_ack()      //应答
{
$      tm1651_dio      in,pull;
tm1651_clk      =0;   tm1651_yanshi();      //第八个时钟的下降沿
while(tm1651_dio){nop;}
tm1651_clk      =1;   tm1651_yanshi();
$      tm1651_dio      out,low;



}
/**************************************************/
void      tm1651_stop()         //结束
{
tm1651_clk      =0;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =1;   tm1651_yanshi();

}
/**************************************************/
/**************************************************/
/**************************************************/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 11, 2021, 05:25:18 pm
I stumbled over a comment on github (all in chinese) which is asking if we want to research the PFC886 together...

There is a repository with source here: https://github.com/stm8stm8stm8/pfc886/blob/main/pwm08b.C (https://github.com/stm8stm8stm8/pfc886/blob/main/pwm08b.C)

Which according to the comment contains code for the "PFC886" IC which is also labeled "MF520".

After following the bread crumbs it turns out that PADAUK offers a special IC for brushless DC motors called the MF520:

http://www.padauk.com.tw/en/product/show.aspx?num=138&kind=44 (http://www.padauk.com.tw/en/product/show.aspx?num=138&kind=44)

In fact this seems to be an 8 core PADAUK with flash support  :) 8)

EDIT:After some more digging I found a video of the "making of" the above source code:

https://www.bilibili.com/video/av712877080/ (https://www.bilibili.com/video/av712877080/)

The video contains some captures of the PFC886 datasheet (again all in chinese :-) )

EDIT2: In the video I was able to see that this IC has 512 byte of RAM  :o

Interesting....

The MF520, MF610 and MF616 all have 8 cores and 512 B RAM, and datasheets on the Padauk website. Unfortunately, these BLDC devices have very brief datasheets. Hope I can find a full PFC886 (or similar - if the MF520 is a PFC886 variant, there might be more PFC devices hidden behind PFC610 and PFC616) datasheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Nominal Animal on June 12, 2021, 04:24:27 am
Please use [CODE] /* Code goes here */ [/CODE], it will be easier to read.
请把[CODE]放在程序之前,[/CODE]放在程序之后。

Code: [Select]
tm1651_clk =0; tm1651_yanshi();
if(tm1651_a1.1){tm1651_dio =1;} else{tm1651_dio =0;}
tm1651_clk =1;tm1651_yanshi();

Perhaps the following instead? 也许以下?
Code: [Select]
#include "extern.h"

tm1651_clk  bit pb.0;
tm1651_dio  bit pb.7;

byte     tm1651_byte;
#define  tm1651_send(b)   { tm1652_byte = b; tm1651_send_byte(); }

void  tm1651_start()
{
    $ tm1651_clk  out,high;   //输出,高
    $ tm1651_dio  out,high;
    .delay 100

    tm1651_dio = 0;
    .delay 100
}

void  tm1651_send_byte()
{
    byte  bits = 8;
    while (bits > 0) {

        tm1651_clk = 0;
        .delay 100

        SR      tm1651_byte$1
        SWAPC   tm1651_dio

        tm1651_clk = 1;
        .delay 100

        bits--;
    }

    //等待确认

    $ tm1651_dio  in,pull;

    tm1651_clk = 0;
    while (tm1651_dio) {
        nop;
    }

    tm1651_clk = 1;
    $ tm1651_dio  out,low;
}

void  tm1651_stop()
{
    tm1651_clk = 0;
    tm1651_dio = 0;
    .delay 100

    tm1651_clk = 1;
    .delay 100

    tm1651_dio = 1;
    .delay 100
}

void   FPPA0 (void)
{
    .ADJUST_IC    SYSCLK=IHRC/4
    $ tm1651_clk  out,high;   //输出,高
    $ tm1651_dio  out,high;

    .delay 100

    while (1) {

        //写数据到显示寄存器,自动地址增加
        tm1651_start();
        tm1651_send(0b0100_0000);
        tm1651_stop();

        //设置地址00H
        tm1651_start();
        tm1651_send(0b1100_0000);
        tm1651_send(0b1111_1111);
        tm1651_send(0b0000_0000);
        tm1651_send(0b0000_1111);
        tm1651_send(0b1111_0000);
        tm1651_stop();

        //显示开,10/16
        tm1651_start();
        tm1651_send(0b1000_1011);
        tm1651_stop();
    }
}
I'm not sure, though, because I do not have any Padauk MCUs, or the Padauk Mini-C compiler; I am just guessing...

I much prefer sdcc.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 12, 2021, 06:50:36 am
IDE0.91: http://www.padauk.com.tw/cn/technical/index.aspx?kind=36 (http://www.padauk.com.tw/cn/technical/index.aspx?kind=36)
单核:Single core processor    :PMS150G,152,154
WITH TOUCH:                      :PMS161,PMS164(FLASH):PFC161
双核:Dual Core Processor      :PMC232,PMC234(FLASH):PFC232
八核:Eight core processor      :(FLASH):PFC886
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 12, 2021, 07:06:39 am
new*new*new*
video:https://www.bilibili.com/video/BV1Bw411Z7fN?from=search&seid=6609710309287088602
/*****************pfc161+tm1651********************/
/******************20210608************************/
/****************qq:774145445**********************/
/****************快手:共同学习stm8*****************/
/**************************************************/
//               _______    ______
//          dio-|1 pb7  \_/  pb010|-clk
//              |2 vdd       gnd 9|
//        cs-||-|3 pa7       pa0 8|-hong
//          tk8-|4 pa6       pa4 7|-lv
//          tk9-|5_pa5_______pa3_6|-lan
//       5v
//  pb0--clk
//  pb7--dio
//       gnd
/**************************************************/
#include   "extern.h"
tm1651_clk      bit      pb.0;
tm1651_dio      bit      pb.7;
/**************************************************/
byte      tm1651_a1;
/**************************************************/
void      tm1651_yanshi();      //延时
void      tm1651_start();         //起始信号
void      tm1651_data();         //数据
void      tm1651_ack();         //应答
void      tm1651_stop();         //结束
/**************************************************/
void   FPPA0 (void)
{
.ADJUST_IC   SYSCLK=IHRC/4      //   SYSCLK=IHRC/4
$      tm1651_clk      out,high;      //输出,高
$      tm1651_dio      out,high;
/**************************************************/
//0x7f;0x30;0x6d;0x79;0x33;0x5b;0x5f;0x70;0x7f;0x7b;0x77;0x1f;0x4e;0x3d;0x4f;0x47;

tm1651_yanshi();
while (1)
{
tm1651_start();
tm1651_a1   =0b0100_0000;   tm1651_data();      //写数据到显示寄存器,自动地址增加
tm1651_stop();
tm1651_start();
tm1651_a1   =0b1100_0000;   tm1651_data();      //设置地址00H
/*
tm1651_a1   =0b1111_1111;   tm1651_data();
tm1651_a1   =0b0000_0000;   tm1651_data();
tm1651_a1   =0b0000_1111;   tm1651_data();
tm1651_a1   =0b1111_0000;   tm1651_data();
*/
tm1651_a1   =0x7e;tm1651_data();
tm1651_a1   =0x30;tm1651_data();
tm1651_a1   =0x6d;tm1651_data();
tm1651_a1   =0x79;tm1651_data();
tm1651_stop();
tm1651_start();
tm1651_a1   =0b1000_1011;   tm1651_data();      //显示开,10/16
tm1651_stop();

//while(1){}
}
}

/**************************************************/
void      tm1651_yanshi()      //延时
{
.delay 100;
}
/**************************************************/
void      tm1651_start()         //起始信号
{
tm1651_clk   =1;   tm1651_dio   =1;   tm1651_yanshi();
tm1651_clk   =1;   tm1651_dio   =0;   tm1651_yanshi();

}
/**************************************************/
void      tm1651_data()         //数据
{

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.0){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.1){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.2){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.3){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.4){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.5){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.6){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a1.7){tm1651_dio   =1;}   else{tm1651_dio   =0;}
tm1651_clk      =1;tm1651_yanshi();



tm1651_ack();

}

/**************************************************/
void      tm1651_ack()      //应答
{
$      tm1651_dio      in,pull;
tm1651_clk      =0;   tm1651_yanshi();      //第八个时钟的下降沿
while(tm1651_dio){nop;}
tm1651_clk      =1;   tm1651_yanshi();
$      tm1651_dio      out,low;



}
/**************************************************/
void      tm1651_stop()         //结束
{
tm1651_clk      =0;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =1;   tm1651_yanshi();

}
/**************************************************/
/**************************************************/
/**************************************************/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 12, 2021, 08:13:18 am
@js_12345678_55AA
mf520data:http://www.padauk.com.tw/cn/product/show.aspx?num=139&kw=520
English:http://www.padauk.com.tw/upload/doc/MF520%20datasheet_EN_V003_20210115.pdf
China:http://www.padauk.com.tw/upload/doc/MF520%20datasheet_CN_V003_20210115.pdf
pfc886 data Chinese only  E-mail:suzhiming@88.com
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 12, 2021, 08:47:14 am
@js_12345678_55AA
This is unpublished data.
E-mail To you.or** 如有业务或工程应用问题, 欢迎联络我司业务窗口 Kevin Liu : kevin_liu@padauk.com.tw **
new:MCS11
http://www.padauk.com.tw/cn/product/show.aspx?num=79&kind=85 (http://www.padauk.com.tw/cn/product/show.aspx?num=79&kind=85)
http://www.padauk.com.tw/upload/doc/MCS11_datasheet_v0%2020_20180420.pdf (http://www.padauk.com.tw/upload/doc/MCS11_datasheet_v0%2020_20180420.pdf)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 12, 2021, 01:20:53 pm
@js_12345678_55AA
This is unpublished data.
E-mail To you.or** 如有业务或工程应用问题, 欢迎联络我司业务窗口 Kevin Liu : kevin_liu@padauk.com.tw **
new:MCS11
http://www.padauk.com.tw/cn/product/show.aspx?num=79&kind=85 (http://www.padauk.com.tw/cn/product/show.aspx?num=79&kind=85)
http://www.padauk.com.tw/upload/doc/MCS11_datasheet_v0%2020_20180420.pdf (http://www.padauk.com.tw/upload/doc/MCS11_datasheet_v0%2020_20180420.pdf)

@suzhiming: 你可以给我发个邮件,js55aa@88.com
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 13, 2021, 09:13:37 am
/*****************pfc161+tm1651********************/
/******************20210608************************/
/****************qq:774145445**********************/
/****************快手:共同学习stm8*****************/
/**************************************************/
//               _______    ______
//          dio-|1 pb7  \_/  pb010|-clk
//              |2 vdd       gnd 9|
//        cs-||-|3 pa7       pa0 8|-hong
//          tk8-|4 pa6       pa4 7|-lv
//          tk9-|5_pa5_______pa3_6|-lan
//       5v
//  pb0--clk
//  pb7--dio
//       gnd
/**************************************************/
#include   "extern.h"
tm1651_clk      bit      pb.0;
tm1651_dio      bit      pb.7;
/**************************************************/
byte      tm1651_a0;
byte      tm1651_a1;
byte      tm1651_a2;
byte      tm1651_a3;
byte      tm1651_a4;
/**************************************************/
void      tm1651_yanshi();      //延时
void      tm1651_start();         //起始信号
void      tm1651_data();         //数据
void      tm1651_ack();         //应答
void      tm1651_stop();         //结束
void      tm1651_xianshi();      //显示
/**************************************************/
void      yanshi()
{
.delay 1000000;
}
void   FPPA0 (void)
{
.ADJUST_IC   SYSCLK=IHRC/4      //   SYSCLK=IHRC/4
$      tm1651_clk      out,high;      //输出,高
$      tm1651_dio      out,high;
/**************************************************/
//0x7e;0x30;0x6d;0x79;0x33;0x5b;0x5f;0x70;0x7f;0x7b;0x77;0x1f;0x4e;0x3d;0x4f;0x47;


while (1)
{
tm1651_a1      =0x7e;
tm1651_a2      =0x30;
tm1651_a3      =0x6d;
tm1651_a4      =0x79;
tm1651_xianshi();
yanshi();

tm1651_a1      =0x33;
tm1651_a2      =0x5b;
tm1651_a3      =0x5f;
tm1651_a4      =0x70;
tm1651_xianshi();
yanshi();

tm1651_a1      =0x7f;
tm1651_a2      =0x7b;
tm1651_a3      =0x77;
tm1651_a4      =0x1f;
tm1651_xianshi();
yanshi();

tm1651_a1      =0x4e;
tm1651_a2      =0x3d;
tm1651_a3      =0x4f;
tm1651_a4      =0x47;
tm1651_xianshi();
yanshi();
}
}

/**************************************************/
void      tm1651_yanshi()      //延时
{
.delay 50;
}
/**************************************************/
void      tm1651_start()         //起始信号
{
tm1651_clk   =1;   tm1651_dio   =1;   tm1651_yanshi();
tm1651_clk   =1;   tm1651_dio   =0;   tm1651_yanshi();

}
/**************************************************/
void      tm1651_data()         //数据
{

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.0){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;      //太快检测不到需要加延时
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.1){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.2){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.3){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.4){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.5){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.6){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();

tm1651_clk      =0;   tm1651_yanshi();
if(tm1651_a0.7){tm1651_dio   =1;}   else{tm1651_dio   =0;}
nop;nop;nop;
tm1651_clk      =1;   tm1651_yanshi();



tm1651_ack();

}

/**************************************************/
void      tm1651_ack()      //应答
{
byte      tm1651_ack_a1;
tm1651_ack_a1      =0;

$      tm1651_dio      in,pull;
tm1651_clk      =0;   tm1651_yanshi();      //第八个时钟的下降沿
while(tm1651_dio==1)      //检测低电平
   {
   tm1651_ack_a1      ++;
   if(tm1651_ack_a1>150)      //退出条件(死机)
      {
      $      tm1651_dio      out,low;
      return;
      }
   }
tm1651_clk      =1;   tm1651_yanshi();
$      tm1651_dio      out,low;



}
/**************************************************/
void      tm1651_stop()         //结束
{
tm1651_clk      =0;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =0;   tm1651_yanshi();
tm1651_clk      =1;   tm1651_dio      =1;   tm1651_yanshi();

}
/**************************************************/
void      tm1651_xianshi()      //显示
{
tm1651_start();
tm1651_a0   =0b0100_0000;   tm1651_data();      //写数据到显示寄存器,自动地址增加
tm1651_stop();
tm1651_start();
tm1651_a0   =0b1100_0000;   tm1651_data();      //设置地址00H
tm1651_a0      =tm1651_a1;   tm1651_data();
tm1651_a0      =tm1651_a2;   tm1651_data();
tm1651_a0      =tm1651_a3;   tm1651_data();
tm1651_a0      =tm1651_a4;   tm1651_data();
tm1651_stop();
tm1651_start();
tm1651_a0   =0b1000_1011;   tm1651_data();      //显示开,10/16
tm1651_stop();
}
/**************************************************/
/**************************************************/
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 14, 2021, 06:33:24 am
thi is assembler And hex,bin  contact
这个是汇编完的效果,asm文件是怎么转换成.bin烧录文件的,这一步是由烧录器完成的
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 16, 2021, 10:47:08 am
It's not a human habit
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 17, 2021, 08:49:11 pm
Hi,

PFC232 write support now uses the "Limited Voltage writing". This makes it possible to use the standard easy-pdk-programmer without modifications.

I also added support for PFC151 and PFC161 ... which are *surprise surprise* ... the *SAME IC*.
Even original writer can write a PFC151 when a PFC161 program is loaded.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 18, 2021, 08:07:45 am
I also added support for PFC151 and PFC161 ... which are *surprise surprise* ... the *SAME IC*.
Even original writer can write a PFC151 when a PFC161 program is loaded.

Looking at the datasheets, the PFC161 one was created by copying the PFC151 one, changing "PFC151" to "PFC161" (though they forgot two places that still have "PFC151") and adding section 11.2 for the capacitive touch peripheral.

I wonder if the PFC161 is a PFC151 with the cacitive touch peripheral added vs. the PFC151 being a PFC161 where the capacitive touch peripheral failed test.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on June 18, 2021, 01:11:40 pm
I wonder if the PFC161 is a PFC151 with the cacitive touch peripheral added vs. the PFC151 being a PFC161 where the capacitive touch peripheral failed test.

...  failed test ...  :-DD :-DD :-DD  What test? Many Padauk data sheets speak about "yield" at programing... basically the customer is doing the test.

Anyway, I will create a small test project to find out. My guess... it is just a marketing variant.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 19, 2021, 05:42:18 am
flash  pfc161
opt    pms61 pms164
http://www.padauk.com.tw/cn/product/index.aspx?kind=61 (http://www.padauk.com.tw/cn/product/index.aspx?kind=61)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 19, 2021, 06:28:00 am
I'd like to try it out.  cannot execute  lack  IDE
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Nominal Animal on June 19, 2021, 09:42:15 am
I'd like to try it out.  cannot execute  lack  IDE
Download and install sdcc-4.1.0-x64-setup.exe (https://sourceforge.net/projects/sdcc/files/sdcc-win64/4.1.0/) first, and then codeblocks-20.03-setup.exe (https://www.codeblocks.org/downloads/binaries/).  Then, Code::Blocks will be your IDE.

If Code::Blocks does not autodetect SDCC, go to 'Settings', 'Global compiler settings' tab, and for 'Selected compiler' pick 'Small Device C Compiler'.  In the 'Toolchain executables' tab, set 'Compiler's installation directory' to 'C:\Program Files\SDCC\'.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 19, 2021, 04:01:09 pm
I'd like to try it out.  cannot execute  lack  IDE

SDCC does not include an IDE. However, some IDEs, such as Code::Blocks do have support for SDCC.

SDCC is basically just a compiler (though it includes standard library, assembler, linker and simulator).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 20, 2021, 07:39:58 am
可以申请样片    You can apply for samples
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 20, 2021, 07:46:08 am
可以用仿真芯片吗?    Can I use a simulation chip?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 20, 2021, 08:50:39 am
可以用仿真芯片吗?    Can I use a simulation chip?

AFAIK, the free toolchain based on SDCC currently does not support the use of the Padauk ICE (in-circuit-emulator).

There are uCsim simulators that come with SDCC, but they are software only and while they do simulate the core, AFAIK support for peripherals is incomplete. Also uCsim currently only supports only the following: PMC153, PMS132B, PMS134. Those have been chosen so that most software for a pdk13/pdk14/pdk15 chip should be able to run on one of them. The uCsim simulators should be very reliable, as they are used for the nightly regression testing (i.e. every night the SDCC compile farm compiles a large number of test programs using the latest SDCC, and executes them using uCsim to detect any possible regressions in SDCC).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: suzhiming on June 22, 2021, 12:02:52 pm
IDE course 使用教程,我不会用
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on July 06, 2021, 10:36:58 am
PCB Manufacturer Support only    <20mb file
我想做一个烧录器,工厂只接受小于20mb文件,仅支持GERBER文件最大外尺寸10*10cm
烧录芯片的文件,现在芯片昂贵,有什么廉价芯片可以代换吗8051,stc,padauk?

The PCB manufacture file is 157 kB (this is <20mb for sure): https://github.com/free-pdk/easy-pdk-programmer-hardware/raw/master/pcb/Gerber_EASYPDKPROG_PCB12_NoSilk.zip

The IC (STM32F072) seems to be available from several sellers for 30-50 RMB: https://s.taobao.com/search?q=STM32F072C8T6

In case you want to be sure to get an original, you could buy a STM32F072 Nucleo board and use the IC from this board (80-100 RMB): https://s.taobao.com/search?q=STM32F072+nucleo
(This would required to modify the PCB since the Nucleo comes with a 64 pin package)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 07, 2021, 01:45:50 am
PCB Manufacturer Support only    <20mb file
我想做一个烧录器,工厂只接受小于20mb文件,仅支持GERBER文件最大外尺寸10*10cm
烧录芯片的文件,现在芯片昂贵,有什么廉价芯片可以代换吗8051,stc,padauk?
You have to use a micro that contains a DAC(NOT PWM) and have a sufficient amount of flash storage. Since the firmware is open source, you can port the firmware to any platform. (What's the license of these codes again?) Make sure you comply the source code license and disclose the source code when needed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 11, 2021, 06:59:35 am
Hi all - I have a few working freepdk programmers (and some that are not so working) and I have recently upgraded my computer (running Linux Mint) to boot from a 1Tb SSD (for speed!). Alas the computer no longer talks to the freepdk programmer (but lsusb and dmesg show it to be present). To help me narrow down the problem solving path, should I be looking for new:

     1. bios firmware
     2. motherboard
     3. power supply
     4. operating system (although the old one worked??)
     5. kernel module
     6. hobby
     7. brain

Note that pulling out the new SSD and booting into the old hard drives did not work.

Any suggestions gratefully accepted - here's some reports from my system

sudo lsusb -v

Code: [Select]
Bus 003 Device 005: ID 0483:5740 STMicroelectronics Virtual COM Port
Device Descriptor:
  bLength                18
  bDescriptorType         1
  bcdUSB               2.00
  bDeviceClass            2 Communications
  bDeviceSubClass         2 Abstract (modem)
  bDeviceProtocol         0
  bMaxPacketSize0        64
  idVendor           0x0483 STMicroelectronics
  idProduct          0x5740 Virtual COM Port
  bcdDevice            2.00
  iManufacturer           1 free-pdk.github.io
  iProduct                2 Easy PDK Programmer
  iSerial                 3 1234567855AA
  bNumConfigurations      1
  Configuration Descriptor:
    bLength                 9
    bDescriptorType         2
    wTotalLength       0x0043
    bNumInterfaces          2
    bConfigurationValue     1
    iConfiguration          0
    bmAttributes         0xc0
      Self Powered
    MaxPower              100mA
    Interface Descriptor:
      bLength                 9
      bDescriptorType         4
      bInterfaceNumber        0
      bAlternateSetting       0
      bNumEndpoints           1
      bInterfaceClass         2 Communications
      bInterfaceSubClass      2 Abstract (modem)
      bInterfaceProtocol      1 AT-commands (v.25ter)
      iInterface              0
      CDC Header:
        bcdCDC               1.10
      CDC Call Management:
        bmCapabilities       0x00
        bDataInterface          1
      CDC ACM:
        bmCapabilities       0x02
          line coding and serial state
      CDC Union:
        bMasterInterface        0
        bSlaveInterface         1
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x82  EP 2 IN
        bmAttributes            3
          Transfer Type            Interrupt
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0008  1x 8 bytes
        bInterval              16
    Interface Descriptor:
      bLength                 9
      bDescriptorType         4
      bInterfaceNumber        1
      bAlternateSetting       0
      bNumEndpoints           2
      bInterfaceClass        10 CDC Data
      bInterfaceSubClass      0
      bInterfaceProtocol      0
      iInterface              0
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x01  EP 1 OUT
        bmAttributes            2
          Transfer Type            Bulk
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0040  1x 64 bytes
        bInterval               0
      Endpoint Descriptor:
        bLength                 7
        bDescriptorType         5
        bEndpointAddress     0x81  EP 1 IN
        bmAttributes            2
          Transfer Type            Bulk
          Synch Type               None
          Usage Type               Data
        wMaxPacketSize     0x0040  1x 64 bytes
        bInterval               0
can't get device qualifier: Resource temporarily unavailable
can't get debug descriptor: Resource temporarily unavailable
Device Status:     0x0001
  Self Powered


dmesg

Code: [Select]
[ 4797.390785] usb 3-10: new full-speed USB device number 5 using xhci_hcd
[ 4797.540232] usb 3-10: New USB device found, idVendor=0483, idProduct=5740, bcdDevice= 2.00
[ 4797.540237] usb 3-10: New USB device strings: Mfr=1, Product=2, SerialNumber=3
[ 4797.540240] usb 3-10: Product: Easy PDK Programmer
[ 4797.540242] usb 3-10: Manufacturer: free-pdk.github.io
[ 4797.540244] usb 3-10: SerialNumber: 1234567855AA
[ 4797.611233] cdc_acm 3-10:1.0: ttyACM0: USB ACM device
[ 4797.611506] usbcore: registered new interface driver cdc_acm
[ 4797.611507] cdc_acm: USB Abstract Control Model driver for USB modems and ISDN adapters

Bovineck (OneCircuit)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: retiredfeline on July 11, 2021, 07:48:01 am
Does your account have permissions on /dev/ttyACM0? Often it's just a matter of making yourself a member of the group that the is the group owner of the try device. The group is often dialup or something like that and the device permissions are often 0664. Sometimes you need to install a udev rule to chgrp and chown the device upon detection when plugged in.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on July 12, 2021, 02:44:33 am
10*10 pcb 拼板已做好,我有j-link,怎么将文件下载到芯片
STM32F072 supports USB-DFU. You don't need a jlink to flash the firmware. Just hold the button while plugging the USB and you should be in the DFU mode. 你不需要jlink来下载固件。STM32F072支持USB-DFU。
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on July 12, 2021, 03:44:35 am
Quote
Does your account have permissions on /dev/ttyACM0? Often it's just a matter of making yourself a member of the group that the is the group owner of the try device. The group is often dialup or something like that and the device permissions are often 0664. Sometimes you need to install a udev rule to chgrp and chown the device upon detection when plugged in.

Wonderful! Thank you that solved the issue.  :)

Bovineck (OneCircuit)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on August 02, 2021, 02:44:56 am
seems like they got a simplified version of their writer. Just like their simplified ICE, the whole PCB is exposed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 11, 2021, 12:02:17 pm
I was happily programming PFS154 chips one day and then the next day...

Code: [Select]
Searching programmer... found: /dev/ttyACM0
FREE-PDK EASY PROG - Hardware:1.2 Firmware:1.3 Protocol:1.3
Erasing IC... done.
Blank check IC... FPDK_ERROR: chip is not blank

If I use --noblank --noverify then calibration fails:

Code: [Select]
Erasing IC... done.
Writing IC (81 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 0Hz (0x00)  out of range.
ERROR: Calibration failed

Different chips and changing the programmer doesn't seem to work.

easyprogtest reports:

Code: [Select]
vdd: 4.93   vpp: 4.98    (vref= 3.30) 

It's a bit of a head scratcher!  :-//

Late addition: my PFS173 chips are fine with the same setup and code - just the PFS154s that are suddenly not cooperative  :(

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 11, 2021, 12:26:30 pm
Quote
Late addition: my PFS173 chips are fine with the same setup and code - just the PFS154s that are suddenly not cooperative  :(

UPDATE: Just those few PFS154 chips. Have thrown them out and performed cleansing ceremony. Sorry for interruption, normal service resumed... :-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 16, 2021, 07:55:31 am
Quote
Late addition: my PFS173 chips are fine with the same setup and code - just the PFS154s that are suddenly not cooperative  :(

UPDATE: Just those few PFS154 chips. Have thrown them out and performed cleansing ceremony. Sorry for interruption, normal service resumed... :-+

Could you ERASE and then READ one of those "faulty" PFS154?

Maybe you wrote something to the "reserved area" (0x7E0-0x7F0) previously. If so, it might be that you turned sections of the flash to READ-ONLY mode. (I found some bits there which disable parts of the flash to be erased/written to. This would explain why you can't erase / write to this ICs properly).

In case this happened to you, I will consider adding a safety feature preventing to write to reserved area (something like an extra command line option like "--write-reserved-area", if not given then write is prohibited).

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 23, 2021, 04:53:13 am
Quote
Could you ERASE and then READ one of those "faulty" PFS154?

They would definitely read, but I'm not sure about erase. I threw them out! Next time I have the same problem I will check.

On a COMPLETELY unrelated matter, how would I compile an assembly file for the PFS154 and write the hex file to the chip?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: retiredfeline on August 23, 2021, 05:16:22 am
SDCC has an assembler. Just run SDCC with the appropriate options (IIRC it does the right thing if the file extension is that of assembler) and it will skip the C compile step. But you still need the startup code so you might want to retain the main() in C and call your assembly code. Or insert inline assembly code in the C code.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bovineck on August 23, 2021, 12:18:47 pm
Quote
SDCC has an assembler. Just run SDCC with the appropriate options (IIRC it does the right thing if the file extension is that of assembler) and it will skip the C compile step. But you still need the startup code so you might want to retain the main() in C and call your assembly code. Or insert inline assembly code in the C code.

I compiled the start-up code with an empty main() and checked out the resulting assembly file that SDCC generated, but then I couldn’t see any way to use it as a template for an assembly version of the start-up code. I’m not sure that method is completely dead for me but I need to spend a lot more time on it.

In the meantime I like the idea of calling assembly code from the C code. It’s more complicated than what I’d like but it’s a nice work around, thank you! I’m not much of a fan of in-line assembly, and I’m not sure why that is!


Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on August 28, 2021, 03:05:18 am
Hello again, everyone.  It's been a while since I posted anything, but I have been following along, and still reach for the Padauk MCUs occasionally for projects.  Part of what has kept me from staying more excited has been the global component shortages and the fact LCSC currently has zero stock of Padauk MCUs.  >:(  Hopefully this is resolved soon.

Anyway, I thought I would post a new 'dev board' that I recently came up with to make breadboard prototyping a bit easier.  One of the challenges has been having to physically move the MCU back and forth between the programmer and the breadboard.  I did come up with the idea of using 1.27mm headers to turn the SOIC MCU into a pluggable module (see my post a few pages back).  This helped, and I do use this with custom PCBs to make easier to test different code versions, but it still seemed a bit too annoying for breadboard prototyping.

This new 'dev board' solves the issue by using two DPDT switches that physically isolate the VDD (ICVDD), PA3 (ICPCK), PA5 (ICVPP), and PC6 (ICPDA) pins during programming from whatever is on the breadboard and vice-versa (see schematic).  This means, all I have to do is flip the switches over towards the 2x4 programming header and run my programming command, and then flip the switches back to the other side to run the code.  I had thought of using CD4053 analog switch ICs at first, but the design was getting too complicated, partly because of the different voltages in play, and I still needed a switch to change modes, so I backed away from that idea for now.

Anyway, here are the gerber files and schematic if anyone wants them.  OSHPARK purchase link: https://oshpark.com/shared_projects/BhdQLc4h (https://oshpark.com/shared_projects/BhdQLc4h). It is designed to work with either the PFS154 or PFS173 16-pin ICs.  Technically it should also work with the PFC154 IC, although I don't have any of those to test with.  I can post these files to a github repo if there is enough interest.

I use a 8-wire IDC cable with 2x4 female connectors on either end.  One end plugs into an adapter that plugs into my easy-pdk-programmer, the other end plugs directly into this dev board.  The DPDT switches are LCSC part number: C108742.  Funny how they cost more than the Padauk MCUs.   :-DD

Oh, yeah, there are also LEDs on PA3/PA4, and a Push Button on PA5/RST that make this ready to go for the examples found in the http://github.com/free-pdk/free-pdk-examples (http://github.com/free-pdk/free-pdk-examples) repo.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on September 03, 2021, 01:24:14 am
https://www.kuaishou.com/f/XTxuFXDaAWv1Wz (https://www.kuaishou.com/f/XTxuFXDaAWv1Wz)

错误就是我应该选win版本就好了,需要.exe文件,软件根本就不会用,有使用指导么?太难了
苏sir你还是发英语吧,用百度翻译一下都好啊。大家都会方便很多。
Please use English while posting on this forum. As most of the members on the forum does not understand Chinese.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 09, 2021, 05:50:20 am
https://www.kuaishou.com/f/X6Eb6Az5izrRf6m (https://www.kuaishou.com/f/X6Eb6Az5izrRf6m)
https://www.kuaishou.com/f/X6Eb6Az5izrRf6m (ftp://www.kuaishou.com/f/X6Eb6Az5izrRf6m)
软件是如何运行的?

How does the software work?

Have you already installed the firmware on the controller? It's described here:

https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Firmware (https://github.com/free-pdk/easy-pdk-programmer-software/tree/master/Firmware)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on September 11, 2021, 11:22:07 am
A few days ago I walked him through with an online meeting. He's now switched to ubuntu for better software support
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: makersLabs on September 12, 2021, 12:14:37 pm
Hi,

This look very good projet and I wanna have programmer for some cheap board later so
I have done assembly for 5 Programmer using provided GERBER files
I successfully program the ST32 chip
I am under windows 10 and also alrdy install the STM32 driver
Using easypdkprog list or --version I get an answer (confirmed version 1.3)
But when I wanna try the probe command the answer is "probing IC... Nothing found" with a PFS154 or PFS173 fresh new chip

This append on all of the programmers, so I guess something wrong :-5
What checking on PCBA can I run to fix this?
What command can I pass to check all?

Rgds
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on September 12, 2021, 12:30:25 pm
Have you tried "easypdkprogtest"  and measured all voltages?
Title: XDT devices?
Post by: spth on September 14, 2021, 07:52:00 am
Recently, about a dozen new Padauk devices becam available at LCSC. Part numbers start with XDT, and I cannot find any datasheets anywhere. They are not mentioned on the Padauk website. The Padauk MINI-C software does not mention them either (there is one XDT device mentioned in there - the XDT0164, but that one isn't among the ones available at LCSC).

Does anyone have any idea about those devices?
Title: Re: XDT devices?
Post by: tim_ on September 14, 2021, 08:06:24 am
Recently, about a dozen new Padauk devices becam available at LCSC. Part numbers start with XDT, and I cannot find any datasheets anywhere. They are not mentioned on the Padauk website. The Padauk MINI-C software does not mention them either (there is one XDT device mentioned in there - the XDT0164, but that one isn't among the ones available at LCSC).

Does anyone have any idea about those devices?

It could be a mistake. All of these seem to be touch controllers without MCU:

http://www.zhienchina.com/product/Touch.html (http://www.zhienchina.com/product/Touch.html)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: makersLabs on September 15, 2021, 08:40:19 am
Have you tried "easypdkprogtest"  and measured all voltages?
Hi Tim,
No I just try to use "normal" program
I found easypdkprgtest.c is it that one you speak about ?

on DOS session sending make easypdgprogtest give me this for result :
D:\Users\FidL\Documents\eagle\easyPDKprog\easy-pdk-programmer-software-master>make easypdkprogtest
cc -std=c99 -pedantic -Wall -O2 -Ilib/argp-standalone-1.3   -c -o serialcom.o serialcom.c
process_begin: CreateProcess(NULL, cc -std=c99 -pedantic -Wall -O2 -Ilib/argp-standalone-1.3 -c -o serialcom.o serialcom.c, ...) failed.
make (e=2): file sp¨|cifi¨| cannot find.
make: *** [serialcom.o] Error 2
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on September 19, 2021, 07:06:58 am
https://item.taobao.com/item.htm?spm=a230r.1.14.1.f1fc51c4BL5XXZ&id=649017329840&ns=1&abbucket=8#detail (https://item.taobao.com/item.htm?spm=a230r.1.14.1.f1fc51c4BL5XXZ&id=649017329840&ns=1&abbucket=8#detail)

XDM4102 and XDM4104. Very interesting. 1.9 KW of program memory. According to the data from Mini-C, these are pdk14 devices. I guess they use the program memory space to map the 2KB EEPROM. That could allow these devices to update their own firmware in the field. It would be great to have datasheets.

P.S.: According to http://www.qy6.com/syjh/showbus8356932.html, (http://www.qy6.com/syjh/showbus8356932.html,) the XDM4105 is basically a PFS173 with EEPROM, the XDM4104 a PFS154 with extra EEPROM , the XDM4103 a PMS152 with extra EEPROM. But according to that page, the program memory has hte full size (so it looks more like two dies in one package). I guess we need to get and decap some to know.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on September 29, 2021, 08:16:09 pm
https://item.taobao.com/item.htm?spm=a230r.1.14.1.f1fc51c4BL5XXZ&id=649017329840&ns=1&abbucket=8#detail (https://item.taobao.com/item.htm?spm=a230r.1.14.1.f1fc51c4BL5XXZ&id=649017329840&ns=1&abbucket=8#detail)

XDM4102 and XDM4104. Very interesting. 1.9 KW of program memory. According to the data from Mini-C, these are pdk14 devices. I guess they use the program memory space to map the 2KB EEPROM. That could allow these devices to update their own firmware in the field. It would be great to have datasheets.

P.S.: According to http://www.qy6.com/syjh/showbus8356932.html, (http://www.qy6.com/syjh/showbus8356932.html,) the XDM4105 is basically a PFS173 with EEPROM, the XDM4104 a PFS154 with extra EEPROM , the XDM4103 a PMS152 with extra EEPROM. But according to that page, the program memory has hte full size (so it looks more like two dies in one package). I guess we need to get and decap some to know.

I have some XDM4103. They are multi chip packages containing a standard PADAUK PMS152 and an attached 24C02 eeprom.
The 24C02 eeprom is attached to IO ports of PADAUK IC. The eeprom can not be used as program memory.
Nothing fancy.

XDM4105 is same thing, a PFS173+24C02 in one package.

Here a list with XDM to PADAUK mapping: http://www.zhienchina.com/product/MCU.html (http://www.zhienchina.com/product/MCU.html)

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 06, 2021, 05:04:15 pm
Hello,

some days ago I had an idea how to add support for writing PDK files (from padauk IDE).

The padauk IDE inserts code that makes a call to almost the end of the IC code memory (e.g. call 0x7FE on PFS154).
If the returned value is 0xFF (ret 0xFF), the calibration code for IHRC is executed.
After WRITER completes the IHRC calibration, it overwrites the return value 0xFF with the calibration value.
The next time IC is started, the same call returns the calibration value, which is then written to IHRCR.

The idea that simplifies PDK support for easypdkprog is that instead of running the complex padauk calibration code, the default easypdk calibration code is embedded and instead of the instruction returning the calibration value, a GOTO to the easypdk calibration code is inserted. This only requires space for 13 additional instructions, which most projects can afford.  8)

The development branch contains an initial implementation that already works very well for all ICs I have tested. The "write" command supports IHX and PDK files now. Even serial numbers (32 bit only) can be set.

For the other direction SDCC .IHX file => usable with padauk IDE I will try a different approach. Instead of converting the .IHX to .PDK, I plan to convert the .IHX to padauk IDE .ASM code (with embedded comments containing original SDCC .C source lines). This converted .ASM code can then be used in padauk IDE to generate PDK files and is also usable with the padauk ICE (padauk emulator).


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on October 09, 2021, 05:43:48 am
@spth



mr.spth
I'm very interested in your open source the programmable hard devices .the operation instructions provided are not clear enough and

I'd like to request some additional documentation regarding the programmer's operation instructions. I'd also like to request the

latest Windows binary development release of the programmer software. annex: Test Chip compatible software
thank you
Su

I can't give it to you because I don't have an import and export certificate.You can buy it on Taobao.
https://item.taobao.com/item.htm?spm=a230r.1.14.1.359b404c0Msywi&id=650818241626&ns=1&abbucket=15#detail (https://item.taobao.com/item.htm?spm=a230r.1.14.1.359b404c0Msywi&id=650818241626&ns=1&abbucket=15#detail)


时间先生


我对你们的开源可编程硬件设备非常感兴趣。提供的操作说明不够清楚,我想要求提供一些关于程序员操作说明的附加文档。我还想申请最新的

Windows二进制开发版本的程序员软件。附件:测试芯片兼容软件

非常感谢。


su
由于我没有进出口凭证,无法给你.你可以在淘宝上购买.
https://item.taobao.com/item.htm?spm=a230r.1.14.1.359b404c0Msywi&id=650818241626&ns=1& (https://item.taobao.com/item.htm?spm=a230r.1.14.1.359b404c0Msywi&id=650818241626&ns=1&)

I didn't create the programmer, and didn't contrinute much to the easypdkprog software either. That work was mostly done by @js_12345678_55AA. But I think you can get help in the forum here or by opening an issue on GitHub.

AFAIK; Windows binaries of releases can be found at https://github.com/free-pdk/easy-pdk-programmer-software/releases (https://github.com/free-pdk/easy-pdk-programmer-software/releases)

I did create the SDCC pdk13, pdk14 and pdk15 backends(s), though: http://sdcc.sourceforge.net (http://sdcc.sourceforge.net) which you can use to compile C code for Padauk µC.

Philipp

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 09, 2021, 07:55:40 pm
mew chip FT32F072C8AT7 LQFP48
https://www.fremontmicro.com/product/32%20bit%20mcu/arm%20core_1/20210316/1769.aspx (https://www.fremontmicro.com/product/32%20bit%20mcu/arm%20core_1/20210316/1769.aspx)
https://item.taobao.com/item.htm?spm=a1z09.2.0.0.df072e8dE6k6EJ&id=656098151997&_u=923hlh4e710 (https://item.taobao.com/item.htm?spm=a1z09.2.0.0.df072e8dE6k6EJ&id=656098151997&_u=923hlh4e710)

So now FMD switched to cloning STM microcontrollers. It would be better if they came up with their own designs instead.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 09, 2021, 07:59:08 pm
Article about Padauk in the Digitimes

https://digitimes.com/news/a20211008PD205.html

"Padauk Technology saw its third-quarter revenue hit a record high of NT$264 million (US$9.43 million), with revenue for the first three quarters of 2021 already exceeding the level in all of 2020."

I wish they would send some reels to LCSC again, but I guess they are busy trying to get enough product for their key customers...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 10, 2021, 03:20:46 pm
Hi

thanks @damingge for the taobao link. I will order some of the FT32F072 to check compatibility and also will try to get some PFC886. For sure it will take some time to export them from China but I have some friends which handle it for me.

Regarding latest "binary versions" of the programmer software / firmware: You always can build it yourself from source. Everything is included. However the next release version will come out soon.
I just wanted to test a bit more all the new features like .PDK writing, support for PFC151/PFC161/PFC232, support for MacSilicon (ARM-Mac) / support for armhf /aarch64 (raspberry pi) ...

JS

Update: I checked FT32F072 data sheet and it looks like it is not at all like a real STM32F072. The SRAM is much smaller, data sheet does not mention dual 12 bit DAC, bootloader does not mention DFU, ... So most likely this is not a valid STM32F072 replacement. I ordered some anyway to have a look myself. Maybe the clone is better than the data sheet.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 12, 2021, 06:43:14 pm
It looks like FMD is planning to have RISC-V products as well:

https://www.fremontmicro.com/product/32%20bit%20mcu/risc-v%20core/index.aspx (https://www.fremontmicro.com/product/32%20bit%20mcu/risc-v%20core/index.aspx)

This could be very interesting. There are still not many small RISC-V devices available.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daming on October 20, 2021, 01:03:42 am
FT32F0 The file is too la.rge. What's your QQ number or email number.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 20, 2021, 08:37:37 pm
FT32F0 The file is too la.rge. What's your QQ number or email number.

You can send to : js55aa@88.com
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on October 23, 2021, 10:15:03 am
This chip is good:

this is:
http://www.wch-ic.com (http://www.wch-ic.com)

http://www.wch.cn/products/category/5.html#data (http://www.wch.cn/products/category/5.html#data)
http://www.wch.cn/products/CH32V103.html? (http://www.wch.cn/products/CH32V103.html?)

This has already been discussed on github. STM32F103 and all its (complicated) clones do not have dual DAC. They also do not have DFU bootloader in ROM which makes programing more complicated.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daming on November 13, 2021, 01:07:21 pm
padauk  new mcu pfc460  26io sop28 tsop28
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: daming on November 13, 2021, 01:15:50 pm
Quad core MCU
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on December 17, 2021, 06:35:40 am
padauk  new mcu pfc460  26io sop28 tsop28
Looks really interesting. If only they were available...

LCSC has some new Padauk MCUs in stock: The PFC161 in various package types. The price is not interesting at all, though (>$0.30).
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on December 31, 2021, 06:34:46 am
Hello,

can anyone tell me where you can buy Padauks (PFS154 and PFS173) right now? I used to buy them at LCSC, but they are out of stock since months. Does anyone knew an alternative platform or when LCSC should have them in stock again?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on January 17, 2022, 09:49:38 pm
It's kinda quiet here...

I am currently trying to make audioplayer work on a PFS154.
However, the example does not work at all. After probing on the SPI line I found that not only the timing is a mess, the padauk is driving the MISO pin which it needs to be listening to instead of driving.

I am wondering this might be a compiler issue since I can't see any pin manipulation on the MISO pin.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 21, 2022, 08:31:50 am
It's kinda quiet here...

I am currently trying to make audioplayer work on a PFS154.
However, the example does not work at all. After probing on the SPI line I found that not only the timing is a mess, the padauk is driving the MISO pin which it needs to be listening to instead of driving.

I am wondering this might be a compiler issue since I can't see any pin manipulation on the MISO pin.

Do you use a recent version of SDCC?

I learned the other day that assembler syntax for IO commands was changed around July 2021 (e.g. "mov.io  IOREG, A" instead of the previous "mov IOREG,A").
=> Recent SDCC versions (snapshot / compiled from source) will most likely produce defect output when assembler language is included in your source code.

You should check the compiler output for warnings about IO register forced to be in memory... (unfortunately the will not be shown with default settings)

To fix this you only need to find all assembler code which contains MOV, T0SN, T1SN, XOR which have an IO register as source or destination. The new syntax for them is "mov.io / t0sn.io / t1sn.io / xor.io"

JS

P.S: Unfortunately updating all existing projects right now is not a good idea, since the stable release version of SDCC does not support the new ".io" syntax :-(


In case you mean the "audioplayer" from showcase projects, you need to change in "pdkspi.c" the assembler function "pdkspi_sendreceive":

Code: [Select]
uint8_t pdkspi_sendreceive(uint8_t s)
{
  __asm
     mov a, #8                                 ; loop 8 times
1$:
     set0.io _ASMS(SPI_PORT), #(SPI_OUT_PIN)   ; SPI-OUT = 0
     t0sn _pdkspi_sendreceive_PARM_1, #7       ; s.7==0 ?
     set1.io _ASMS(SPI_PORT), #(SPI_OUT_PIN)   ; SPI-OUT = 1
     set1.io _ASMS(SPI_PORT), #(SPI_CLK_PIN)   ; SPI-CLK = 1
     sl _pdkspi_sendreceive_PARM_1             ; s<<=1
     t0sn.io _ASMS(SPI_PORT), #(SPI_IN_PIN)    ; SPI-IN==0 ?
     set1 _pdkspi_sendreceive_PARM_1, #0       ; s.0=1
     set0.io _ASMS(SPI_PORT), #(SPI_CLK_PIN)   ; SPI-CLK = 0
     dzsn a                                    ; loop--
     goto 1$                                   ; loop again if>0
  __endasm;
  return s;
}

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on January 21, 2022, 12:00:42 pm
I changed all showcase projects: https://github.com/free-pdk/easy-pdk-showcase-projects

They now use the new .io assembler syntax and require a recent SDCC version (>=4.1.10) for compilation.

I also added a workaround in the polysound project for the compiler bug / regression with incorrect working scoping of enums ( https://sourceforge.net/p/sdcc/bugs/3289/ )

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on February 04, 2022, 11:16:11 am
P.S: Unfortunately updating all existing projects right now is not a good idea, since the stable release version of SDCC does not support the new ".io" syntax :-(

You could use e.g.

Code: [Select]
#if __SDCC_REVISION >= 12558
mov.io-style asm code
#else
mov-style asm code
#endif
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 09, 2022, 03:20:15 pm
Yesterday, SDCC 4.2.0 was released. There were no fancy new features particularly relevant to the pdk ports, though.

Development continues after the release , and the STM8 just got support for ISO C23 bit-precise integer types. Those could be useful for Padauk devices once ported, as they allow e.g. the use of 24-bit and 40-bit integer types.
P.S.: SDCC also allows bit-fields of bit-precise integer types, so they are also a way to have bit-fields wider than int.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 25, 2022, 03:26:42 pm
Just a quick update, PMS150C(both SOP-8 and SOT-23-6) is back in stock in lcsc with sufficient stock.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on April 28, 2022, 03:48:03 pm
Stock depleting, be quick if you still wanna pick up some PMS150C!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on June 17, 2022, 08:23:57 pm
There's a new category on Padauk's website called PML series
There are some speculation that it might be a new series of low power (or even single cell battery?) MCU.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on June 25, 2022, 06:31:51 pm
Datasheets for the PML100 have been published. Looks like the L stands for "LED", not "low power", as the PML100 has "One set triple 11bit SuLED (Super LED) PWM generators and timers".
Though operating current at 1 MHz is also 50% lower than for the PMC150. And power save current (stopexe) is much lower than PMC150 (5 µA vs 400 µA). Power down current (stopsys) is slightly higher, though.

P.S.: Interestingly, despite the memory sizes covered by the pdk13 architecture, this is actually a pdk14 device, as we can see from the "ASM_INSTR SYM_85A" in PML100.INC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: Slartibartfast123 on August 18, 2022, 03:36:56 pm
The PFS172/173 series seems to be discontinued and no longer available. The follow up is the PFS122/123 series which only seems to have a 12bit ADC instead of the 8bit ADC. At least the PFS122 is available right now:

https://lcsc.com/search?q=pfs122

Will there be a support in easypdkprog too?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: socram on August 19, 2022, 01:16:39 am
The PFS172/173 series seems to be discontinued and no longer available. The follow up is the PFS122/123 series which only seems to have a 12bit ADC instead of the 8bit ADC. At least the PFS122 is available right now:

https://lcsc.com/search?q=pfs122

Will there be a support in easypdkprog too?
Those look particularly interesting - reading through the datasheet they have a "limited voltage programming mode" where it uses 5.0V volts only, which means a simpler programmer with no voltage shifting shenanigans could be doable.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on August 22, 2022, 02:53:54 pm
The PFS172/173 series seems to be discontinued and no longer available. The follow up is the PFS122/123 series which only seems to have a 12bit ADC instead of the 8bit ADC. At least the PFS122 is available right now:
https://lcsc.com/search?q=pfs122
Will there be a support in easypdkprog too?
Support can be added as soon as I can get hold of some ICs.

Those look particularly interesting - reading through the datasheet they have a "limited voltage programming mode" where it uses 5.0V volts only, which means a simpler programmer with no voltage shifting shenanigans could be doable.
In the development branch you can see already some devices (e.g. PFC151/PFC161/PFC154/PFS172/PFC232) which use limited voltage programing mode.

The main gist of limited voltage programing mode is that VPP is set to 0V during programing phase (only VDD of apx. 4.8V needs to be supplied).
However to activate the special programing mode you still need 2 different voltages for VDD and VPP where VDD < VPP-1.5V
So yes... this would make it possible to omit the DCDC booster, but setting variable output voltages for VDD and VPP is still a thing.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on September 25, 2022, 11:37:03 pm
Hi JS, do i see this correct that you could have VDD switchable between 3.3V and 5V,
and to activate 'special programming mode' you could do VDD 3.3V, VPP 5V.
Then later set VDD to 5V ?
on-board switching between 3.3V and 5V, with a reasonably low current, could probably even be done with an analog switch ..

I would like to use padauks (PFC154,PFC232,PFS122) in multiple projects now. Ideally programmable in the board, by higher level micro.

Happy to support the development efforts not only with praise but also with material.

We will do a WS2812B output driver and an I2C software slave.

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on September 26, 2022, 02:31:08 am
Attachment NY8AO51H Timings
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on September 27, 2022, 10:50:23 am
Attachment NY8AO51H Timings

Thank You.

Now I have working write and read :)

I made BIN decoder.
Start decoding from configuration words (0x76 in BIN; "xdat", 4B len, 32B configuration words, 2048B data....)
Output: 1024W data, 16W config.

"ny_dec(buffer, 16+1024);"

Code: [Select]
uint16_t nop_bin[16+1024] = {
0xF8E5, 0x269D, 0xE258, 0xBC49, 0x7987, 0xA2DE, 0x4B2F, 0x74E7, 0x5035, 0x3ACD, 0x75A6, 0x55F9, 0xB4DF, 0xA969, 0x74FA, 0x98F6,
0xB372, 0x3850, 0x28FF, 0xFAE5, 0x114A, 0x067A, 0x8AE0, 0x6E5D, 0x5B98, 0x10EE, 0xFC57, 0x018E, 0xAA34, 0x3EEB, 0xB9B1, 0x3FE8,
0x1FB8, 0xF516, 0x8C97, 0x3541, 0xAB8B, 0xAB60, 0xA9EB, 0x9F77, 0x2C11, 0xFBBA, 0x7E49, 0x4A19, 0xB4F9, 0xF44C, 0xFF1D, 0x5725,
0xBB1C, 0x34D9, 0x962D, 0x3EEC, 0x81A8, 0x2291, 0xFD9C, 0x819C, 0xBB93, 0x36F1, 0xD957, 0xE6D3, 0x79BF, 0x5024, 0x30B9, 0xEDE4,
0x1606, 0x17D2, 0x6707, 0x4965, 0x6AFC, 0xA08F, 0xB60B, 0x9F51, 0x7134, 0x705D, 0xB19A, 0x4277, 0xB870, 0x4A9E, 0x3B14, 0xC7C7,
0x9FF7, 0x43A5, 0x79EC, 0xDEE7, 0xA7B7, 0x0791, 0x1AC1, 0x5217, 0xD55C, 0xBFF9, 0x0B5B, 0xEF6D, 0x9B7B, 0xBBB4, 0x4C9D, 0x2C93,
0x1DE9, 0x0832, 0x6721, 0x1440, 0xE11B, 0x6F5C, 0xBE65, 0x93D8, 0xCFE6, 0xB454, 0x2178, 0x669C, 0xCF0C, 0xA55F, 0xDB1F, 0xE1D8,
0xBAF7, 0xA4F8, 0xAA67, 0xB028, 0x2EBF, 0xD59D, 0x137F, 0xB0D3, 0x3ECC, 0xC3DD, 0xCA2C, 0xE482, 0x849B, 0xBB92, 0x11B8, 0xA774,
0xD23A, 0x005C, 0x6BA8, 0xAA92, 0x2512, 0xFFBE, 0x9A8E, 0xE4A4, 0x2027, 0x545F, 0x0767, 0x439C, 0x2851, 0x76D4, 0xB5D0, 0x68D0,
0x68FB, 0xAD46, 0x48A3, 0x5BB8, 0x529B, 0x14EA, 0x1890, 0xAF33, 0x3EEA, 0x9EF8, 0x41CB, 0x2B51, 0x8CF5, 0xB71B, 0xAF6A, 0x637D,
0x42D8, 0x24B7, 0x1CD4, 0x4553, 0xC519, 0xD9A1, 0xBF8E, 0x03F9, 0xF3AC, 0x3A90, 0x8E6F, 0x9190, 0x21EF, 0x9410, 0x5E40, 0x14F4,
0xA98C, 0xA6A9, 0x5743, 0x5B9E, 0x0FBE, 0x9F0D, 0xD743, 0xA75D, 0x3263, 0x202A, 0x85C2, 0xBBB3, 0xA81E, 0xC067, 0x40AB, 0x8376,
0x64C7, 0x01B7, 0xFB89, 0x96D8, 0xABD6, 0x50A9, 0x6D82, 0x0A47, 0x1168, 0xD100, 0xF24B, 0x50E7, 0x2A00, 0x8BF0, 0x5E66, 0x49D1,
0x226B, 0x697A, 0x5F2D, 0x5717, 0xB16C, 0x5B04, 0x47A1, 0x83B6, 0x451F, 0xCFEB, 0x65C9, 0x9DAC, 0x8D1E, 0x273A, 0x9320, 0xEDB9,
0xEDCF, 0xD3BB, 0xF237, 0x741C, 0x4046, 0x2C8D, 0xACF5, 0x01A8, 0x0E88, 0xD126, 0xAF6E, 0xDB00, 0xE5D3, 0x839E, 0x52EF, 0xF703,
0xE662, 0xF998, 0x7BC6, 0x206B, 0x5EAD, 0xBB0F, 0x61BE, 0xA6B6, 0xA242, 0x1C60, 0x0B06, 0x14A4, 0x5F12, 0x2E84, 0x71E4, 0x0629,
0x91EB, 0x12CC, 0xF9D8, 0x6BFC, 0x4060, 0x71A8, 0x2712, 0xCE7B, 0x06E6, 0xDDAF, 0x11BC, 0x1F09, 0x7531, 0xA775, 0x2593, 0x18C2,
0x0669, 0xDF87, 0x5EC6, 0xC736, 0x8D26, 0xD5C0, 0xE8B6, 0x74BA, 0xABFC, 0xFEA4, 0xE096, 0x6880, 0x9E65, 0x256B, 0x6E04, 0x060F,
0xCCCE, 0x992B, 0x360B, 0x6392, 0x4CE9, 0xCF7A, 0xE31B, 0x5E99, 0x220D, 0xAAD3, 0xFE7D, 0xFF02, 0x532E, 0x8275, 0xC2CE, 0xCB49,
0x68A6, 0x568F, 0x8CCA, 0xCE88, 0x6FE2, 0x3E50, 0x9492, 0xB5CD, 0xA013, 0xE144, 0xE0B0, 0x35A5, 0x1582, 0xEAB8, 0x666A, 0x0A86,
0x721C, 0x5D22, 0xA6E9, 0x4779, 0x3B95, 0x20BB, 0x0310, 0x7886, 0x070D, 0x4D8E, 0x2DF6, 0x91CD, 0xDA26, 0x5079, 0xCB70, 0x298D,
0x8336, 0x2AAB, 0x4DBD, 0xC567, 0x7002, 0x3E76, 0xC9B7, 0x3E2A, 0x6FC0, 0xE92A, 0xEC39, 0x8B77, 0xD18B, 0x7A5A, 0x4281, 0x7DFA,
0x9DDD, 0xBD29, 0x80F6, 0x6279, 0xDCC8, 0xF330, 0x6DDF, 0xF18E, 0xD501, 0x4430, 0xCF32, 0x7A5D, 0xA602, 0x910E, 0xC09F, 0x366D,
0x8310, 0x778E, 0xC65A, 0x0AB4, 0x786C, 0x32FF, 0x7765, 0xFA23, 0xFF22, 0xCDC1, 0x9B45, 0x64B6, 0x3180, 0x5C45, 0x6781, 0x9AA7,
0x4E56, 0xD3E6, 0x09FE, 0xB075, 0xD576, 0x11F4, 0x864F, 0x8DAA, 0x1476, 0x4FDF, 0xD0D2, 0x7A7B, 0xFB27, 0x1AE9, 0x0F4C, 0x3E03,
0x8F99, 0xC95C, 0x0253, 0x9A56, 0x5C87, 0x4583, 0x98A4, 0x1A28, 0xD93D, 0xE8C1, 0x7C18, 0xB73D, 0x5F4F, 0xD54D, 0xB58D, 0x9319,
0xAC92, 0x3876, 0x75DA, 0x7102, 0xDE99, 0x0E14, 0x8669, 0xD08F, 0x9F91, 0x800C, 0xD8BC, 0x76F2, 0x45F5, 0xDEE0, 0x9FAE, 0x1AE8,
0xF8E5, 0x269D, 0xE258, 0xBC49, 0x7987, 0xA2DE, 0x4B2F, 0x74E7, 0x5035, 0x3ACD, 0x75A6, 0x55F9, 0xB4DF, 0xA969, 0x74FA, 0x98F6,
0xB372, 0x3850, 0x28FF, 0xFAE5, 0x114A, 0x067A, 0x8AE0, 0x6E5D, 0x5B98, 0x10EE, 0xFC57, 0x018E, 0xAA34, 0x3EEB, 0xB9B1, 0x3FE8,
0x1FB8, 0xF516, 0x8C97, 0x3541, 0xAB8B, 0xAB60, 0xA9EB, 0x9F77, 0x2C11, 0xFBBA, 0x7E49, 0x4A19, 0xB4F9, 0xF44C, 0xFF1D, 0x5725,
0xBB1C, 0x34D9, 0x962D, 0x3EEC, 0x81A8, 0x2291, 0xFD9C, 0x819C, 0xBB93, 0x36F1, 0xD957, 0xE6D3, 0x79BF, 0x5024, 0x30B9, 0xEDE4,
0x1606, 0x17D2, 0x6707, 0x4965, 0x6AFC, 0xA08F, 0xB60B, 0x9F51, 0x7134, 0x705D, 0xB19A, 0x4277, 0xB870, 0x4A9E, 0x3B14, 0xC7C7,
0x9FF7, 0x43A5, 0x79EC, 0xDEE7, 0xA7B7, 0x0791, 0x1AC1, 0x5217, 0xEC2E, 0x16DE, 0x1A38, 0xB0BC, 0x7C78, 0x2BB1, 0x16F2, 0xECB8,
0x743E, 0x07AD, 0xCDE1, 0x63C8, 0x55B2, 0x5621, 0xFAE4, 0x0666, 0xF694, 0x1D73, 0x301B, 0x394D, 0x280F, 0x355A, 0x8170, 0x21F3,
0xD320, 0xAB67, 0x00A7, 0xC7A0, 0x9A16, 0xECE0, 0x57FE, 0x256D, 0x07BE, 0x6AFA, 0xDB4F, 0xBB53, 0x6398, 0x2B97, 0x4BD7, 0x675F,
0xBBED, 0x0FC3, 0xC168, 0xDD1A, 0x91BB, 0xC6C3, 0xDE0F, 0x711A, 0x1955, 0xFD78, 0x1604, 0x1C4D, 0xCF52, 0xE6D1, 0xEFBF, 0xA8FB,
0x012C, 0xA2D9, 0xE263, 0x2C30, 0xE632, 0x2D97, 0x5C11, 0x3A8D, 0x0798, 0x37DF, 0x50A8, 0x7480, 0x6BF6, 0x271E, 0xF505, 0xA356,
0x2B0F, 0x2B28, 0xB614, 0x32DB, 0x71B0, 0xE0DC, 0xFB0F, 0x9647, 0xCADE, 0x93B7, 0x9F0C, 0xCE41, 0xC6EC, 0x0415, 0x042F, 0xD4DF,
0xC05B, 0xA936, 0xFD83, 0x2C16, 0xBB17, 0xA670, 0x93C2, 0x32E3, 0x0B11, 0x890D, 0x94A1, 0xE462, 0x4F1D, 0x5062, 0x1AC4, 0x435D,
0x0D10, 0x0E28, 0x5149, 0xE150, 0x1F7F, 0x69D4, 0x2903, 0x9FF9, 0x281A, 0x7827, 0xE328, 0x0F36, 0xCD03, 0x1BF5, 0x0409, 0x89FA,
0x4BBC, 0x66E5, 0xF5ED, 0x209F, 0x05C5, 0x6279, 0x0320, 0x1608, 0x7C6D, 0x66CC, 0x74AA, 0xC27D, 0x6A1D, 0xB73F, 0xC94F, 0x2D92,
0x8418, 0xDC24, 0x58F7, 0x0394, 0xF4EF, 0x15F0, 0xE874, 0x9416, 0x37FA, 0x7801, 0xBE0D, 0x84D1, 0x02D0, 0x139B, 0x0880, 0x3728,
0x8FB5, 0xF607, 0xD106, 0x57E3, 0xEA04, 0x8272, 0x253F, 0x3308, 0x9B30, 0xB547, 0x1A65, 0x4B75, 0xB811, 0xBE81, 0x2B8B, 0xC602,
0xF83C, 0x1D53, 0x5318, 0x1C74, 0xF4C9, 0x48D5, 0x6393, 0x5BC5, 0x3F94, 0x7488, 0x00DF, 0x40D8, 0x9232, 0x3770, 0x7FFC, 0xD8E9,
0x6FBE, 0xD018, 0xF406, 0xB0BE, 0x398F, 0xECBD, 0xAC37, 0xE104, 0x928E, 0x5783, 0xF1F5, 0x3751, 0x7966, 0xB56E, 0x346B, 0xC624,
0xA519, 0x96B4, 0x9CCB, 0x141A, 0xF840, 0xF607, 0xA79A, 0xCB27, 0x1B7F, 0x03F4, 0xEF1E, 0xA0D3, 0xB42D, 0x1270, 0x98A1, 0x0B62,
0x0171, 0x5910, 0x260A, 0xB900, 0xDB4B, 0x072D, 0xD013, 0x2073, 0x9961, 0x4863, 0xF1D3, 0x6A74, 0xF281, 0x7ABD, 0x3C05, 0xCAAD,
0x1BCB, 0x52BD, 0x0C29, 0x30F1, 0x8F3C, 0x19C6, 0x4791, 0xED38, 0x3E7F, 0xE4A9, 0x3C95, 0xCE1C, 0x3D25, 0xC07C, 0x911F, 0xE9A6,
0xEAE1, 0x2534, 0xE77D, 0xB2EF, 0xC4AB, 0x070B, 0x8D36, 0xAB94, 0x56B2, 0x400D, 0xFD5A, 0xD4A6, 0x3688, 0xEA5F, 0x18EE, 0xBDD1,
0xF40A, 0xB2B6, 0x2A36, 0x15F1, 0x6861, 0xCA4D, 0x295E, 0x6430, 0xEC73, 0xED17, 0xDE51, 0x258C, 0x4101, 0x010B, 0x9AF0, 0xF646,
0xEAC7, 0x7811, 0x6C9A, 0x7D3C, 0xCCC5, 0x0B82, 0x33E4, 0x6F9D, 0xC650, 0x64E6, 0x8A26, 0x3B67, 0xD683, 0xCC40, 0x3DEE, 0x5A8C,
0x2781, 0xDC79, 0xA33E, 0xC7FD, 0x61DF, 0x2889, 0xC2CE, 0x1814, 0x2D04, 0xE6F8, 0xC1B1, 0x25AA, 0x1C24, 0x8AEC, 0x5523, 0xFE28,
0xE64E, 0xC6C3, 0xA893, 0xEDDE, 0xE82E, 0x7CFE, 0xDC25, 0x8F96, 0xE04F, 0x41E6, 0x6D7B, 0xE8EC, 0xB84C, 0x4548, 0xEFE2, 0x5332,
0xC545, 0x37E9, 0xDF1A, 0x068A, 0x6A30, 0x3769, 0xC2E8, 0x4531, 0xA6E3, 0x292B, 0xC9DF, 0x2923, 0xA2F6, 0x4EE5, 0xC5C1, 0xDAC3,
0x9132, 0x2902, 0x4898, 0xCBC1, 0xCD2E, 0x9BA3, 0x0FAE, 0xE159, 0x6947, 0x93EA, 0x64C5, 0x0A28, 0x53DC, 0x396C, 0x2E95, 0x58DD,
0xDAA5, 0x37CF, 0x823F, 0x8D6D, 0xA5E3, 0x3F07, 0xCE61, 0xFBE3, 0x62EA, 0xB9C9, 0xED34, 0x5E5F, 0x4D37, 0xAEEE, 0xE3DE, 0xFFC3,
0x766F, 0xFA89, 0x2657, 0x42C9, 0x1F22, 0x921D, 0xED6A, 0x0AC9, 0x1563, 0x529D, 0x6F2A, 0x15C8, 0x53FA, 0x6449, 0xA572, 0x970E,
0xD2CB, 0x3B46, 0x3CED, 0x4964, 0x3501, 0x1BEC, 0xB91D, 0x1422, 0x82E1, 0x9FD6, 0xC834, 0xB902, 0x9EBC, 0xC021, 0x6AD6, 0x2DCF,
0x7FD1, 0x184D, 0xCDC7, 0x3EED, 0xDE55, 0x99F2, 0xF28A, 0x0AEF, 0x4846, 0xD97A, 0xA0F9, 0x1DA6, 0x5F73, 0xDA9B, 0x617B, 0x07EC,
0xF620, 0x4C3A, 0xD32C, 0xA96F, 0x131E, 0x3EEC, 0x5E40, 0xC7A9, 0xEC2E, 0x16DE, 0x1A38, 0xB0BC, 0x7C78, 0x2BB1, 0x16F2, 0xECB8,
0x743E, 0x07AD, 0xCDE1, 0x63C8, 0x55B2, 0x5621, 0xFAE4, 0x0666, 0xF694, 0x1D73, 0x301B, 0x394D, 0x280F, 0x355A, 0x8170, 0x21F3,
0xD320, 0xAB67, 0x00A7, 0xC7A0, 0x9A16, 0xECE0, 0x57FE, 0x256D, 0x07BE, 0x6AFA, 0xDB4F, 0xBB53, 0x6398, 0x2B97, 0x4BD7, 0x675F,
0xBBED, 0x0FC3, 0xC168, 0xDD1A, 0x91BB, 0xC6C3, 0xDE0F, 0x711A, 0x1955, 0xFD78, 0x1604, 0x1C4D, 0xCF52, 0xE6D1, 0xEFBF, 0xA8FB,
0x012C, 0xA2D9, 0xE263, 0x2C30, 0xE632, 0x2D97, 0x5C11, 0x3A8D, 0x0798, 0x37DF, 0x50A8, 0x7480, 0x6BF6, 0x271E, 0xF505, 0xA356,
0x2B0F, 0x2B28, 0xB614, 0x32DB, 0x71B0, 0xE0DC, 0xFB0F, 0x9647, 0xCADE, 0x93B7, 0x9F0C, 0xCE41, 0xC6EC, 0x0415, 0x042F, 0xDADF
};

void ny_dec(uint16_t *data, uint16_t cnt){
uint16_t i, t[1024+16];
uint8_t a, b;

for(i=0; i<cnt; i++) t[1023+16-i] = data[i] ^ nop_bin[i];

for(i=0; i<cnt; i++){
a = t[i];
b = t[i]>>8;

if(i>=0x208){
b = (b >> 2) | (b << (8-2));
a = (a >> 6) | (a << (8-6));
}
else{
a = (a >> 3) | (a << (8-3));
b = (b >> 5) | (b << (8-5));
}

data[i] = a<<8 | b;
data[i] &= 0x3FFF;
}
}


https://youtube.com/watch?v=HRjVPssgL48 (https://youtube.com/watch?v=HRjVPssgL48)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on September 29, 2022, 07:19:25 am
I don't know how to privately send you attachments on this site,
At this time, please download the attachment I re-uploaded.
Also I don't understand English, I used google translate.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on October 04, 2022, 03:35:59 am
Whoa! Is that a Nyquest flasher? Does this means that we can flash Nyquest NY8 with EasyPadaukProgrammer hardware?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on October 04, 2022, 07:21:36 am
Nyquest NY8A051H *.BIN decoder.
I'm not sure it's 100% correct, but it's a start.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: hidden on October 07, 2022, 02:29:01 am
Attachment NY8AO51H Timings

Thank You.

Now I have working write and read :)

I made BIN decoder.
Start decoding from configuration words (0x76 in BIN; "xdat", 4B len, 32B configuration words, 2048B data....)
Output: 1024W data, 16W config.

"ny_dec(buffer, 16+1024);"

Code: [Select]
uint16_t nop_bin[16+1024] = {
0xF8E5, 0x269D, 0xE258, 0xBC49, 0x7987, 0xA2DE, 0x4B2F, 0x74E7, 0x5035, 0x3ACD, 0x75A6, 0x55F9, 0xB4DF, 0xA969, 0x74FA, 0x98F6,
0xB372, 0x3850, 0x28FF, 0xFAE5, 0x114A, 0x067A, 0x8AE0, 0x6E5D, 0x5B98, 0x10EE, 0xFC57, 0x018E, 0xAA34, 0x3EEB, 0xB9B1, 0x3FE8,
0x1FB8, 0xF516, 0x8C97, 0x3541, 0xAB8B, 0xAB60, 0xA9EB, 0x9F77, 0x2C11, 0xFBBA, 0x7E49, 0x4A19, 0xB4F9, 0xF44C, 0xFF1D, 0x5725,
0xBB1C, 0x34D9, 0x962D, 0x3EEC, 0x81A8, 0x2291, 0xFD9C, 0x819C, 0xBB93, 0x36F1, 0xD957, 0xE6D3, 0x79BF, 0x5024, 0x30B9, 0xEDE4,
0x1606, 0x17D2, 0x6707, 0x4965, 0x6AFC, 0xA08F, 0xB60B, 0x9F51, 0x7134, 0x705D, 0xB19A, 0x4277, 0xB870, 0x4A9E, 0x3B14, 0xC7C7,
0x9FF7, 0x43A5, 0x79EC, 0xDEE7, 0xA7B7, 0x0791, 0x1AC1, 0x5217, 0xD55C, 0xBFF9, 0x0B5B, 0xEF6D, 0x9B7B, 0xBBB4, 0x4C9D, 0x2C93,
0x1DE9, 0x0832, 0x6721, 0x1440, 0xE11B, 0x6F5C, 0xBE65, 0x93D8, 0xCFE6, 0xB454, 0x2178, 0x669C, 0xCF0C, 0xA55F, 0xDB1F, 0xE1D8,
0xBAF7, 0xA4F8, 0xAA67, 0xB028, 0x2EBF, 0xD59D, 0x137F, 0xB0D3, 0x3ECC, 0xC3DD, 0xCA2C, 0xE482, 0x849B, 0xBB92, 0x11B8, 0xA774,
0xD23A, 0x005C, 0x6BA8, 0xAA92, 0x2512, 0xFFBE, 0x9A8E, 0xE4A4, 0x2027, 0x545F, 0x0767, 0x439C, 0x2851, 0x76D4, 0xB5D0, 0x68D0,
0x68FB, 0xAD46, 0x48A3, 0x5BB8, 0x529B, 0x14EA, 0x1890, 0xAF33, 0x3EEA, 0x9EF8, 0x41CB, 0x2B51, 0x8CF5, 0xB71B, 0xAF6A, 0x637D,
0x42D8, 0x24B7, 0x1CD4, 0x4553, 0xC519, 0xD9A1, 0xBF8E, 0x03F9, 0xF3AC, 0x3A90, 0x8E6F, 0x9190, 0x21EF, 0x9410, 0x5E40, 0x14F4,
0xA98C, 0xA6A9, 0x5743, 0x5B9E, 0x0FBE, 0x9F0D, 0xD743, 0xA75D, 0x3263, 0x202A, 0x85C2, 0xBBB3, 0xA81E, 0xC067, 0x40AB, 0x8376,
0x64C7, 0x01B7, 0xFB89, 0x96D8, 0xABD6, 0x50A9, 0x6D82, 0x0A47, 0x1168, 0xD100, 0xF24B, 0x50E7, 0x2A00, 0x8BF0, 0x5E66, 0x49D1,
0x226B, 0x697A, 0x5F2D, 0x5717, 0xB16C, 0x5B04, 0x47A1, 0x83B6, 0x451F, 0xCFEB, 0x65C9, 0x9DAC, 0x8D1E, 0x273A, 0x9320, 0xEDB9,
0xEDCF, 0xD3BB, 0xF237, 0x741C, 0x4046, 0x2C8D, 0xACF5, 0x01A8, 0x0E88, 0xD126, 0xAF6E, 0xDB00, 0xE5D3, 0x839E, 0x52EF, 0xF703,
0xE662, 0xF998, 0x7BC6, 0x206B, 0x5EAD, 0xBB0F, 0x61BE, 0xA6B6, 0xA242, 0x1C60, 0x0B06, 0x14A4, 0x5F12, 0x2E84, 0x71E4, 0x0629,
0x91EB, 0x12CC, 0xF9D8, 0x6BFC, 0x4060, 0x71A8, 0x2712, 0xCE7B, 0x06E6, 0xDDAF, 0x11BC, 0x1F09, 0x7531, 0xA775, 0x2593, 0x18C2,
0x0669, 0xDF87, 0x5EC6, 0xC736, 0x8D26, 0xD5C0, 0xE8B6, 0x74BA, 0xABFC, 0xFEA4, 0xE096, 0x6880, 0x9E65, 0x256B, 0x6E04, 0x060F,
0xCCCE, 0x992B, 0x360B, 0x6392, 0x4CE9, 0xCF7A, 0xE31B, 0x5E99, 0x220D, 0xAAD3, 0xFE7D, 0xFF02, 0x532E, 0x8275, 0xC2CE, 0xCB49,
0x68A6, 0x568F, 0x8CCA, 0xCE88, 0x6FE2, 0x3E50, 0x9492, 0xB5CD, 0xA013, 0xE144, 0xE0B0, 0x35A5, 0x1582, 0xEAB8, 0x666A, 0x0A86,
0x721C, 0x5D22, 0xA6E9, 0x4779, 0x3B95, 0x20BB, 0x0310, 0x7886, 0x070D, 0x4D8E, 0x2DF6, 0x91CD, 0xDA26, 0x5079, 0xCB70, 0x298D,
0x8336, 0x2AAB, 0x4DBD, 0xC567, 0x7002, 0x3E76, 0xC9B7, 0x3E2A, 0x6FC0, 0xE92A, 0xEC39, 0x8B77, 0xD18B, 0x7A5A, 0x4281, 0x7DFA,
0x9DDD, 0xBD29, 0x80F6, 0x6279, 0xDCC8, 0xF330, 0x6DDF, 0xF18E, 0xD501, 0x4430, 0xCF32, 0x7A5D, 0xA602, 0x910E, 0xC09F, 0x366D,
0x8310, 0x778E, 0xC65A, 0x0AB4, 0x786C, 0x32FF, 0x7765, 0xFA23, 0xFF22, 0xCDC1, 0x9B45, 0x64B6, 0x3180, 0x5C45, 0x6781, 0x9AA7,
0x4E56, 0xD3E6, 0x09FE, 0xB075, 0xD576, 0x11F4, 0x864F, 0x8DAA, 0x1476, 0x4FDF, 0xD0D2, 0x7A7B, 0xFB27, 0x1AE9, 0x0F4C, 0x3E03,
0x8F99, 0xC95C, 0x0253, 0x9A56, 0x5C87, 0x4583, 0x98A4, 0x1A28, 0xD93D, 0xE8C1, 0x7C18, 0xB73D, 0x5F4F, 0xD54D, 0xB58D, 0x9319,
0xAC92, 0x3876, 0x75DA, 0x7102, 0xDE99, 0x0E14, 0x8669, 0xD08F, 0x9F91, 0x800C, 0xD8BC, 0x76F2, 0x45F5, 0xDEE0, 0x9FAE, 0x1AE8,
0xF8E5, 0x269D, 0xE258, 0xBC49, 0x7987, 0xA2DE, 0x4B2F, 0x74E7, 0x5035, 0x3ACD, 0x75A6, 0x55F9, 0xB4DF, 0xA969, 0x74FA, 0x98F6,
0xB372, 0x3850, 0x28FF, 0xFAE5, 0x114A, 0x067A, 0x8AE0, 0x6E5D, 0x5B98, 0x10EE, 0xFC57, 0x018E, 0xAA34, 0x3EEB, 0xB9B1, 0x3FE8,
0x1FB8, 0xF516, 0x8C97, 0x3541, 0xAB8B, 0xAB60, 0xA9EB, 0x9F77, 0x2C11, 0xFBBA, 0x7E49, 0x4A19, 0xB4F9, 0xF44C, 0xFF1D, 0x5725,
0xBB1C, 0x34D9, 0x962D, 0x3EEC, 0x81A8, 0x2291, 0xFD9C, 0x819C, 0xBB93, 0x36F1, 0xD957, 0xE6D3, 0x79BF, 0x5024, 0x30B9, 0xEDE4,
0x1606, 0x17D2, 0x6707, 0x4965, 0x6AFC, 0xA08F, 0xB60B, 0x9F51, 0x7134, 0x705D, 0xB19A, 0x4277, 0xB870, 0x4A9E, 0x3B14, 0xC7C7,
0x9FF7, 0x43A5, 0x79EC, 0xDEE7, 0xA7B7, 0x0791, 0x1AC1, 0x5217, 0xEC2E, 0x16DE, 0x1A38, 0xB0BC, 0x7C78, 0x2BB1, 0x16F2, 0xECB8,
0x743E, 0x07AD, 0xCDE1, 0x63C8, 0x55B2, 0x5621, 0xFAE4, 0x0666, 0xF694, 0x1D73, 0x301B, 0x394D, 0x280F, 0x355A, 0x8170, 0x21F3,
0xD320, 0xAB67, 0x00A7, 0xC7A0, 0x9A16, 0xECE0, 0x57FE, 0x256D, 0x07BE, 0x6AFA, 0xDB4F, 0xBB53, 0x6398, 0x2B97, 0x4BD7, 0x675F,
0xBBED, 0x0FC3, 0xC168, 0xDD1A, 0x91BB, 0xC6C3, 0xDE0F, 0x711A, 0x1955, 0xFD78, 0x1604, 0x1C4D, 0xCF52, 0xE6D1, 0xEFBF, 0xA8FB,
0x012C, 0xA2D9, 0xE263, 0x2C30, 0xE632, 0x2D97, 0x5C11, 0x3A8D, 0x0798, 0x37DF, 0x50A8, 0x7480, 0x6BF6, 0x271E, 0xF505, 0xA356,
0x2B0F, 0x2B28, 0xB614, 0x32DB, 0x71B0, 0xE0DC, 0xFB0F, 0x9647, 0xCADE, 0x93B7, 0x9F0C, 0xCE41, 0xC6EC, 0x0415, 0x042F, 0xD4DF,
0xC05B, 0xA936, 0xFD83, 0x2C16, 0xBB17, 0xA670, 0x93C2, 0x32E3, 0x0B11, 0x890D, 0x94A1, 0xE462, 0x4F1D, 0x5062, 0x1AC4, 0x435D,
0x0D10, 0x0E28, 0x5149, 0xE150, 0x1F7F, 0x69D4, 0x2903, 0x9FF9, 0x281A, 0x7827, 0xE328, 0x0F36, 0xCD03, 0x1BF5, 0x0409, 0x89FA,
0x4BBC, 0x66E5, 0xF5ED, 0x209F, 0x05C5, 0x6279, 0x0320, 0x1608, 0x7C6D, 0x66CC, 0x74AA, 0xC27D, 0x6A1D, 0xB73F, 0xC94F, 0x2D92,
0x8418, 0xDC24, 0x58F7, 0x0394, 0xF4EF, 0x15F0, 0xE874, 0x9416, 0x37FA, 0x7801, 0xBE0D, 0x84D1, 0x02D0, 0x139B, 0x0880, 0x3728,
0x8FB5, 0xF607, 0xD106, 0x57E3, 0xEA04, 0x8272, 0x253F, 0x3308, 0x9B30, 0xB547, 0x1A65, 0x4B75, 0xB811, 0xBE81, 0x2B8B, 0xC602,
0xF83C, 0x1D53, 0x5318, 0x1C74, 0xF4C9, 0x48D5, 0x6393, 0x5BC5, 0x3F94, 0x7488, 0x00DF, 0x40D8, 0x9232, 0x3770, 0x7FFC, 0xD8E9,
0x6FBE, 0xD018, 0xF406, 0xB0BE, 0x398F, 0xECBD, 0xAC37, 0xE104, 0x928E, 0x5783, 0xF1F5, 0x3751, 0x7966, 0xB56E, 0x346B, 0xC624,
0xA519, 0x96B4, 0x9CCB, 0x141A, 0xF840, 0xF607, 0xA79A, 0xCB27, 0x1B7F, 0x03F4, 0xEF1E, 0xA0D3, 0xB42D, 0x1270, 0x98A1, 0x0B62,
0x0171, 0x5910, 0x260A, 0xB900, 0xDB4B, 0x072D, 0xD013, 0x2073, 0x9961, 0x4863, 0xF1D3, 0x6A74, 0xF281, 0x7ABD, 0x3C05, 0xCAAD,
0x1BCB, 0x52BD, 0x0C29, 0x30F1, 0x8F3C, 0x19C6, 0x4791, 0xED38, 0x3E7F, 0xE4A9, 0x3C95, 0xCE1C, 0x3D25, 0xC07C, 0x911F, 0xE9A6,
0xEAE1, 0x2534, 0xE77D, 0xB2EF, 0xC4AB, 0x070B, 0x8D36, 0xAB94, 0x56B2, 0x400D, 0xFD5A, 0xD4A6, 0x3688, 0xEA5F, 0x18EE, 0xBDD1,
0xF40A, 0xB2B6, 0x2A36, 0x15F1, 0x6861, 0xCA4D, 0x295E, 0x6430, 0xEC73, 0xED17, 0xDE51, 0x258C, 0x4101, 0x010B, 0x9AF0, 0xF646,
0xEAC7, 0x7811, 0x6C9A, 0x7D3C, 0xCCC5, 0x0B82, 0x33E4, 0x6F9D, 0xC650, 0x64E6, 0x8A26, 0x3B67, 0xD683, 0xCC40, 0x3DEE, 0x5A8C,
0x2781, 0xDC79, 0xA33E, 0xC7FD, 0x61DF, 0x2889, 0xC2CE, 0x1814, 0x2D04, 0xE6F8, 0xC1B1, 0x25AA, 0x1C24, 0x8AEC, 0x5523, 0xFE28,
0xE64E, 0xC6C3, 0xA893, 0xEDDE, 0xE82E, 0x7CFE, 0xDC25, 0x8F96, 0xE04F, 0x41E6, 0x6D7B, 0xE8EC, 0xB84C, 0x4548, 0xEFE2, 0x5332,
0xC545, 0x37E9, 0xDF1A, 0x068A, 0x6A30, 0x3769, 0xC2E8, 0x4531, 0xA6E3, 0x292B, 0xC9DF, 0x2923, 0xA2F6, 0x4EE5, 0xC5C1, 0xDAC3,
0x9132, 0x2902, 0x4898, 0xCBC1, 0xCD2E, 0x9BA3, 0x0FAE, 0xE159, 0x6947, 0x93EA, 0x64C5, 0x0A28, 0x53DC, 0x396C, 0x2E95, 0x58DD,
0xDAA5, 0x37CF, 0x823F, 0x8D6D, 0xA5E3, 0x3F07, 0xCE61, 0xFBE3, 0x62EA, 0xB9C9, 0xED34, 0x5E5F, 0x4D37, 0xAEEE, 0xE3DE, 0xFFC3,
0x766F, 0xFA89, 0x2657, 0x42C9, 0x1F22, 0x921D, 0xED6A, 0x0AC9, 0x1563, 0x529D, 0x6F2A, 0x15C8, 0x53FA, 0x6449, 0xA572, 0x970E,
0xD2CB, 0x3B46, 0x3CED, 0x4964, 0x3501, 0x1BEC, 0xB91D, 0x1422, 0x82E1, 0x9FD6, 0xC834, 0xB902, 0x9EBC, 0xC021, 0x6AD6, 0x2DCF,
0x7FD1, 0x184D, 0xCDC7, 0x3EED, 0xDE55, 0x99F2, 0xF28A, 0x0AEF, 0x4846, 0xD97A, 0xA0F9, 0x1DA6, 0x5F73, 0xDA9B, 0x617B, 0x07EC,
0xF620, 0x4C3A, 0xD32C, 0xA96F, 0x131E, 0x3EEC, 0x5E40, 0xC7A9, 0xEC2E, 0x16DE, 0x1A38, 0xB0BC, 0x7C78, 0x2BB1, 0x16F2, 0xECB8,
0x743E, 0x07AD, 0xCDE1, 0x63C8, 0x55B2, 0x5621, 0xFAE4, 0x0666, 0xF694, 0x1D73, 0x301B, 0x394D, 0x280F, 0x355A, 0x8170, 0x21F3,
0xD320, 0xAB67, 0x00A7, 0xC7A0, 0x9A16, 0xECE0, 0x57FE, 0x256D, 0x07BE, 0x6AFA, 0xDB4F, 0xBB53, 0x6398, 0x2B97, 0x4BD7, 0x675F,
0xBBED, 0x0FC3, 0xC168, 0xDD1A, 0x91BB, 0xC6C3, 0xDE0F, 0x711A, 0x1955, 0xFD78, 0x1604, 0x1C4D, 0xCF52, 0xE6D1, 0xEFBF, 0xA8FB,
0x012C, 0xA2D9, 0xE263, 0x2C30, 0xE632, 0x2D97, 0x5C11, 0x3A8D, 0x0798, 0x37DF, 0x50A8, 0x7480, 0x6BF6, 0x271E, 0xF505, 0xA356,
0x2B0F, 0x2B28, 0xB614, 0x32DB, 0x71B0, 0xE0DC, 0xFB0F, 0x9647, 0xCADE, 0x93B7, 0x9F0C, 0xCE41, 0xC6EC, 0x0415, 0x042F, 0xDADF
};

void ny_dec(uint16_t *data, uint16_t cnt){
uint16_t i, t[1024+16];
uint8_t a, b;

for(i=0; i<cnt; i++) t[1023+16-i] = data[i] ^ nop_bin[i];

for(i=0; i<cnt; i++){
a = t[i];
b = t[i]>>8;

if(i>=0x208){
b = (b >> 2) | (b << (8-2));
a = (a >> 6) | (a << (8-6));
}
else{
a = (a >> 3) | (a << (8-3));
b = (b >> 5) | (b << (8-5));
}

data[i] = a<<8 | b;
data[i] &= 0x3FFF;
}
}


https://youtube.com/watch?v=HRjVPssgL48 (https://youtube.com/watch?v=HRjVPssgL48)
(https://files.catbox.moe/ua6x4g.png)
Does anyone know what is wrong in my attachment?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: piotr_go on October 07, 2022, 07:54:53 am
You don't read anything to decode.
You have to read BIN first (from 0x76).
"nop_bin" is xor table, not data to decode.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on October 22, 2022, 12:11:27 pm
So, i got a first board with PFC154 working and its mostly in-circuit programmable with the lite-r1 (i interrupt the VDD pin for programming).

Now i am trying to do an efficient WS1812B driver, in assembler, and an i2c slave (interrupt driven) within SDCC framework.

So far so good.

I will help where i can answering questions.

J.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 05, 2022, 07:28:39 pm
Where is the activity regarding Nyquest suddenly coming from? I noticed you can now buy plenty of their devices very cheaply on LCSC. It looks like they are basically PIC clones? They are supported by SDCC?

Also, many Padauk devices are in stock again at normal prices! Most interesting is the PMS154C-S16, which is well supported by the OS toolchain.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 06, 2022, 05:12:59 pm
There have been a few new devices recently: the current Padauk IDE mentions a PFC887, there are datasheets for PFC440, PMS15B, PMB180, PGS134, PGS152. I've added some github fppa documentation repo today.

But I wonder if the instruction encoding used on PFC886 and PFC887 is really the same as other pdk16 devices: the .INC files call it SYM83B2, while for the older pdk16 devices, it is called SYM83A.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on November 09, 2022, 08:52:28 am
Hello together
I wanted to ask if the  PFC161 is supported by SDCC and the free pdk programmer at the time.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on November 10, 2022, 08:23:49 am
Hello together
I wanted to ask if the  PFC161 is supported by SDCC and the free pdk programmer at the time.

It is. easypdkprog added support in June 2021, SDCC has had support since spring 2019.
I'd still recommend to use a recent version of easypdkprog and a recent release (e.g. SDCC 4.2.0) of SDCC.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on November 16, 2022, 05:05:55 am
Thank you :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rs04 on November 16, 2022, 10:28:19 pm
Hello everybody,
  The EEVblog community has made the padauk programmer which I have and used it. I also have the 5S-I-S02B padauk provided emulator. For testing my programs I use this emulator using the IDE provided by padauk itself which supports mini c language.
   My question is, can I convert this mini-c programmed code to the ihex file supported by the freepdk programmer? If not I have to first check the code in emulator, then write the same code for sdcc compiler which does not feel good to me.
  The IC that I am working with is PMS171B which is OTP type and I can not reprogrammed it to fix any minor mistake for which I have to use emulator. I also tried converting the mini-c code into asm code and copy the code in sdcc compatible way using  "__asm" and end it. But during compilation it shows error. While converting mini-c to asm, some commands with "???" will also appear which I removed.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on November 23, 2022, 03:53:31 am
something worth mentioning in the newer padauk IDE. They are using a key and response system for the customer service to unlock clients that can not connect to the internet. Might be a fun investigation if someone is interested. The way to access the unlock dialog is to run a fresh IDE without internet connection and click Help > News
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on November 23, 2022, 04:11:34 am
Where is the activity regarding Nyquest suddenly coming from? I noticed you can now buy plenty of their devices very cheaply on LCSC. It looks like they are basically PIC clones? They are supported by SDCC?
Correct, they are PIC clones. Their NY8 C compiler uses a modified SDCC without following the GPL open source license by opening the source code of the modified tool chain.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 23, 2022, 07:59:10 am
something worth mentioning in the newer padauk IDE. They are using a key and response system for the customer service to unlock clients that can not connect to the internet. Might be a fun investigation if someone is interested. The way to access the unlock dialog is to run a fresh IDE without internet connection and click Help > News

So the new IDE is locked down? It really seems that Padauk is not appreciating the open market...

I am having a good time with the CH32V003. It's a minimal RISC-V (RV32EC) microcontroller that is only $0.10 and comes with an excellent free toolchain. Not to speak of an overabundance of periphery including DMA...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 23, 2022, 08:00:40 am
Where is the activity regarding Nyquest suddenly coming from? I noticed you can now buy plenty of their devices very cheaply on LCSC. It looks like they are basically PIC clones? They are supported by SDCC?
Correct, they are PIC clones. Their NY8 C compiler uses a modified SDCC without following the GPL open source license by opening the source code of the modified tool chain.

Ok, that explains. I saw references to the SDCC toolchain in their examples with a target called "ny8", that is not supported by the official SDCC. Annoying, and not something that should be supported.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on November 24, 2022, 01:59:12 am
something worth mentioning in the newer padauk IDE. They are using a key and response system for the customer service to unlock clients that can not connect to the internet. Might be a fun investigation if someone is interested. The way to access the unlock dialog is to run a fresh IDE without internet connection and click Help > News

So the new IDE is locked down? It really seems that Padauk is not appreciating the open market...

I am having a good time with the CH32V003. It's a minimal RISC-V (RV32EC) microcontroller that is only $0.10 and comes with an excellent free toolchain. Not to speak of an overabundance of periphery including DMA...
Not really, it's just an alternative way of network activation. If there's a working internet connection the activation process is automatic and transparent to the user.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on November 24, 2022, 04:30:40 am
also, seems like they just released some MCU with EEPROM or lithium charger.
They are also planning to release some hall effect switches next year.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on November 24, 2022, 06:46:09 am
also, seems like they just released some MCU with EEPROM or lithium charger.
They are also planning to release some hall effect switches next year.

Catalogue in english:
http://www.padauk.com.tw//upload/SelectionGuide/Company_Catalogue_2023H1_v2_20221124..pdf (http://www.padauk.com.tw//upload/SelectionGuide/Company_Catalogue_2023H1_v2_20221124..pdf)

Interesting, they seem to pursue lots of opportunities where they combine their small MCU core with other devices. It also seems that they plan to discontinue many parts that are still listed on their website like the PFS173.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: rs04 on November 25, 2022, 10:36:33 am
I want to program PFC161 using freePDK hardware. For this I need to use the development branch. Using the firmware of master branch does not support in development branch. But there is no
EASYPDKPROG.dfu file in this branch. Where can I get it?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 02, 2022, 02:17:30 pm
I want to program PFC161 using freePDK hardware. For this I need to use the development branch. Using the firmware of master branch does not support in development branch. But there is no
EASYPDKPROG.dfu file in this branch. Where can I get it?

Build it via "make" in Firmware/source?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 04, 2022, 10:38:42 pm
Hi, 
i have a PFC154-S16 on a board which does not identify correctly:

TYPE:FLASH RSP:0xE34B VPP=4.50 VDD=2.00

Unsupported IC

For me this smells as if padauk made a new mask version and counted up 34A to 34B - could that be ?
Any advice how to debug this further ?

I have ICs i can send to whoever can take a look ..

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 06, 2022, 04:42:46 pm
Hi JS,

i can send you PFS122 via DHL quickly (within europe), we bought a good quantity of -S16 and -U08

I have quite some parts stocked now in Portugal - i believe in using those padauks for several projects, so we bought stock to have them.

Plus - i want to use them commercially so happy to send you a bounty to get this moving.

Johannes

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 06, 2022, 05:31:16 pm
Reply to self :(

The problem is understood but not solved. The chip has no issue and identifies correctly

Our motherboard has 'just' a 10k pullup to the Padauk supply on the programming pins, but that already causes the programming interface to get wrong bits apparently and fail. I assume its some critical timing in the programmer firmware, a 10k pullup should actually not have any influence on a digital signal like that programming data pin. 

We use easypdk 'lite' with 100 ohm series resistors in the programming lines, removing those does not change anything.

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 06, 2022, 09:50:15 pm
Reply to self :(

The problem is understood but not solved. The chip has no issue and identifies correctly

Our motherboard has 'just' a 10k pullup to the Padauk supply on the programming pins, but that already causes the programming interface to get wrong bits apparently and fail. I assume its some critical timing in the programmer firmware, a 10k pullup should actually not have any influence on a digital signal like that programming data pin.

We use easypdk 'lite' with 100 ohm series resistors in the programming lines, removing those does not change anything.

Johannes
Hi,

Hard to give any advise on this. In circuit programing was and always will be a challange with PADAUK ICs. Even the PADAUK official programer gives you a hrad challange here.

You mentioned pull up resistors on the programing data pins. This could in fact be a problem. Since you pull up those pins to 5.5V (VDD during programing of PFC154) it will be harder for PADAUK IC to properly to pull them down to signal a 0. The STM32 is a 3.3V IC with 5V tolerant pins. But this does not mean that the logic level of STM32's inputs is translated as well... So in case the PADAUK IC can not pull down the "0" bit below 1.23V then it is undefined what actually will be read.

From your post it looks like the "probe" command already has bit problems.
Since the probe command uses extra low voltage it might be a good idea to change the firmware code for your scenario and use higher VDD / VPP:

firmware: "fpdk.c"
Code: [Select]
uint32_t FPDK_ProbeIC(FPDKICTYPE* type, uint32_t* vpp_cmd, uint32_t* vdd_cmd)
{
  //try to get IC with low voltages
  *vpp_cmd = 4500; *vdd_cmd = 2000;
...
You can try to increase those values slightly to compensate for pull ups / downs in your circuit. E.g. try to set vpp_cmd to 5500 and vdd_cmd to 2500 or 3000 and check if probing is working with your circuit. Note: This is just for the probe command.

The actual read/write/erase command and programing voltages are defined within the
host software: "fpdkicdata.c"

Code: [Select]
{ .name                                      = "PFC154",
   .otpid                                     = 0x2AA5,
   .id12bit                                   = 0x34A,
   .type                                      = FPDK_IC_FLASH,
   .addressbits                               = 13,
...
   .vdd_cmd_read                              = 2.5,
   .vpp_cmd_read                              = 5.5,
   .vdd_read_hv                               = 2.5,
   .vpp_read_hv                               = 5.5,
...
   .vdd_cmd_write                             = 2.5,
   .vpp_cmd_write                             = 5.5,
   .vdd_write_hv                              = 5.5,
   .vpp_write_hv                              = 0.0,
...

For programing phase 1 (command phase) which is used to identify the IC vdd_cmd_write and vpp_cmd_write are used.
In case you get an error that the IC does not match when you try to write, you can experiment with those values.
You might want to increade / decrease them for some milivolts. Just make sure vdd_cmd_write + 2.5V < vpp_cmd_write (this is the "magic" to enable PADAUK programing mode).

JS

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 08, 2022, 12:21:47 pm
I did some more investigation about the programming problem with the pullup on the padauk PFC154 ('in circuit programming').

My suspicion proves correct, it is the pullup on the data line (PA6). The other pins used for programming are not affected.

It is super easy to reproduce, if you just add a 10kOhm pullup between PA6 and VDD on a sip test socket with a PFC154 and plug that to easyprog lite. it cannot identify the chip properly.
The error seems to be just in the last bit of the ID, and with the scope i verified that the levels of the bits seem correct.

So my assumption is that this can be fixed in software on easyprog, it is probably an issue of sampling timing of the answer, and it is not an issue of the padauk pin (not being able to drive against 10k or the like).

attached
- picture of setup (with easyprog and pfc154 and the pullup)
- picture of signals on scope without pullup
- picture of signals on scope with pullup.

I dont know the exact serial programming protocol of the padauk, but i can investigate into the firmware of the programmer and probably figure this out, however, i assume some of you are much faster on this.

Johannes

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 09, 2022, 08:07:02 pm
Hi JS,

i can send you PFS122 via DHL quickly (within europe), we bought a good quantity of -S16 and -U08

I have quite some parts stocked now in Portugal - i believe in using those padauks for several projects, so we bought stock to have them.

Plus - i want to use them commercially so happy to send you a bounty to get this moving.

Johannes

Have you tried your PFS122 with easypdkprog?

The ones I purchased identify as PFS172, reading, writing, running... all works fine.
They also can be written as PFS172 with official PADAUK WRITER.

And last but not least... in official PADAUK IDE if you look at the header files, PFS172.INC and PFS122.INC are identical. PFS122 just adds some extra definitions for ADCM (ADC modes).

Checking OTP_ID we learn:

PFS121, PFS122, PFS172, PFS172B are all the SAME IC.

PFS123, PFS173, PFS173B are all the SAME IC


So looks like PFS122 support was there all the time  :-DD

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 09, 2022, 09:43:10 pm
I did some more investigation about the programming problem with the pullup on the padauk PFC154 ('in circuit programming').

My suspicion proves correct, it is the pullup on the data line (PA6). The other pins used for programming are not affected.

It is super easy to reproduce, if you just add a 10kOhm pullup between PA6 and VDD on a sip test socket with a PFC154 and plug that to easyprog lite. it cannot identify the chip properly.
The error seems to be just in the last bit of the ID, and with the scope i verified that the levels of the bits seem correct.

So my assumption is that this can be fixed in software on easyprog, it is probably an issue of sampling timing of the answer, and it is not an issue of the padauk pin (not being able to drive against 10k or the like).

attached
- picture of setup (with easyprog and pfc154 and the pullup)
- picture of signals on scope without pullup
- picture of signals on scope with pullup.

I dont know the exact serial programming protocol of the padauk, but i can investigate into the firmware of the programmer and probably figure this out, however, i assume some of you are much faster on this.

Johannes

When I do the same experiment (10K between VDD and PA6) I get the exact same problem.

As a test I modified the clock timing in firmware (fpdk.c: _FPDK_DelayUS() 1 => 20) and changed the timeouts in host software (fpdkcom.c: FPDKCOM_CMDRSP_READIC_TIMEOUT 10000 / FPDKCOM_CMDRSP_WRITE_TIMEOUT 20000).
This did not change the wrong OTPID problem (last bit different). Then I changed the IC OTP ID inside of fpdkicdata.c and to my suprise a read worked (it only works with the slower timing). Erase also worked.
Write starts but somehow the result looks very bad (not just bit failures, it seems to write to wrong places).

However, with some more experiments this might have a solution after all.


JS

EDIT: There is a PULL-DOWN config for the GPIO-INPUT config for the DAT line (PA.6) when STM32 is reading bits. When I change this to PULL-UP I get the same result as when the external PULL-UP 10k resistor is connected.
This makes me believe that PFC 14 bit series might clock out 1 ID bit less and the last bit interpreted as ID is in fact a floating DAT line (PADAUK does not push/pull this bit).
After looking at the OTP-ID we have right now for PFC154: 0x34A and shifting it 1 bit to the right we get 0x1A5 (which is in line with other OTP IDs, matching in parts the OTP ID we find in PADAUK header files. PFC154 OTP_ID in PADAUK header: 0x2AA5).
So it should be possible to solve the ID bit without changing the timing...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 10, 2022, 06:12:28 pm
 ;D i will try the PFS122 on monday, just got a first PCB with it (for testing i used the PFC232 on the boards) into the office.
*** GOOD NEWS indeed !

On the PFC14, thanks for investigating ! I tried modifying the ID also (added 'PFC154B to the list) and it worked for identification, but programming did not, and i am not the specialist (yet).

Breaking my fingers now on the optimized I2C state machine, interrupt based ..



Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 13, 2022, 06:33:55 pm
OK, so i have a full feature I2C implementation, interrupt based, working.
It simulates the usual PCF8574 but it also 'makes' a second device with 16 generic registers plus some readonly info for identification.
All works 100% in interrupt context, so the 'main' program is free for other functions.
There is a 'notification callback' when the PCF8574 is written so the main program can take action.

I will test the code a bit and clean it up. I will eventually publish it as open source, if someone is interested i can share it now.

One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register. So if a specific bit (in my case i2c data) is set to 0, but 'input', the set bit instruction on any other IO bit in that port will result .. in the 0 being changed to 1 (by readback of the input with '1 value and write out). It is logical but caught me .. 

last comment (actually this is a question): i would like to use the "SWAPC" instruction, but did not get that to compile (well .. assemble). Is that maybe missing or is there a specific syntax i am missing ?
I tried SWAPC and also SWAPC.io, neither worked.

Cheers

Johannes

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on December 13, 2022, 06:59:56 pm
OK, so i have a full feature I2C implementation, interrupt based, working.
It simulates the usual PCF8574 but it also 'makes' a second device with 16 generic registers plus some readonly info for identification.
All works 100% in interrupt context, so the 'main' program is free for other functions.
There is a 'notification callback' when the PCF8574 is written so the main program can take action.

I will test the code a bit and clean it up. I will eventually publish it as open source, if someone is interested i can share it now.

One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register. So if a specific bit (in my case i2c data) is set to 0, but 'input', the set bit instruction on any other IO bit in that port will result .. in the 0 being changed to 1 (by readback of the input with '1 value and write out). It is logical but caught me .. 

last comment (actually this is a question): i would like to use the "SWAPC" instruction, but did not get that to compile (well .. assemble). Is that maybe missing or is there a specific syntax i am missing ?
I tried SWAPC and also SWAPC.io, neither worked.

Cheers

Johannes

I would definitely be interested to see your i2c implementation at some point.

I have my own that works pretty good up to about 370 kHz, although it requires a host with clock stretching compatibility.  I haven't published it anywhere yet, partly due to laziness, and partly because it uses the SWAPC instruction that as you have noticed is broken with the current version of SDCC.

You can try the previous version of SDCC to get SWAPC to compile, but they I believe you will have to also revert all the .IO syntax.  There is an outstanding bug report about the issue here: https://sourceforge.net/p/sdcc/bugs/3376/.  Hopefully it is resolved for the next release.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bonnom on December 13, 2022, 07:07:45 pm

Checking OTP_ID we learn:

PFS121, PFS122, PFS172, PFS172B are all the SAME IC.

PFS123, PFS173, PFS173B are all the SAME IC


So looks like PFS122 support was there all the time  :-DD

JS

I also noticed that, they discontinued the, PFS121, PFS172, PFS172B, PFS173, PFS173B and replaced them with PFS122 and PFS123.
Maybe they had some problems with the ADC accuracy and decided not to sell them as 12-bit ADCs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: bonnom on December 13, 2022, 07:11:05 pm
OK, so i have a full feature I2C implementation, interrupt based, working.
It simulates the usual PCF8574 but it also 'makes' a second device with 16 generic registers plus some readonly info for identification.
All works 100% in interrupt context, so the 'main' program is free for other functions.
There is a 'notification callback' when the PCF8574 is written so the main program can take action.

I will test the code a bit and clean it up. I will eventually publish it as open source, if someone is interested i can share it now.

One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register. So if a specific bit (in my case i2c data) is set to 0, but 'input', the set bit instruction on any other IO bit in that port will result .. in the 0 being changed to 1 (by readback of the input with '1 value and write out). It is logical but caught me .. 

last comment (actually this is a question): i would like to use the "SWAPC" instruction, but did not get that to compile (well .. assemble). Is that maybe missing or is there a specific syntax i am missing ?
I tried SWAPC and also SWAPC.io, neither worked.

Cheers

Johannes

Could you check if you can flash the PFS122 with the easy-pdk-prog with the PFS172 flag.
If that works we can add PFS122 to easy-pdk-prog and have official support!

edit: forget to say flag
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 14, 2022, 04:40:54 pm

Could you check if you can flash the PFS122 with the easy-pdk-prog with the PFS172 flag.
If that works we can add PFS122 to easy-pdk-prog and have official support!

edit: forget to say flag

I already checked that and it worked... Then I was unsure if the seller might have mixed up something, so I went to the original "PADAUK_Tool" include files and saw that they all share the same OTP_ID. The OTP_ID is used from original PDAUK_IDE during compilation and embedded inside of the .PDK file. The OTP_ID is the only thing original "PADAUK Writer" uses to check if the correct IC is present.

Means: "Same OTP ID in header files = same IC silicon is used". There are no PFS121, PFS122, PFS172B... there is only the PFS172 ;-)

And in case they would have corrected something in some component (making a new mask) for sure they would have changed the OTP ID in this case.

JS

BTW: I already added PFS121, PFS122, ... as "variant names" to easypdkprog (development branch). SO you can flash them as "PFS121" / "PFS122" / ...
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 14, 2022, 05:34:24 pm
You can try the previous version of SDCC to get SWAPC to compile, but they I believe you will have to also revert all the .IO syntax.  There is an outstanding bug report about the issue here: https://sourceforge.net/p/sdcc/bugs/3376/.  Hopefully it is resolved for the next release.

I had a quick look at it and added a patch for the swapc bug (https://sourceforge.net/p/sdcc/bugs/3376/). It was introduced with the .io syntax change.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 14, 2022, 11:21:40 pm
So i can confirm the PFS122 perfectly programs 'as' PFS172.

Note - PFS122 has a 12bit 'R-type' ADC and is sold as such. It is less accurate than the 'real' ADC which is for example in the PFS232, and it can only use VDD as reference voltage, but it works well for what i do with the PFS122 (a PoE+ inrush controller which limits inrush to PoE levels on a PoE+ device so it can be used on PoE switches without problems, with limited power of course).
Note: the PFS122 include files are missing the ADC low four bit result register, resp. use the 8-bit name for the high ..

THANKS for the swapc patch. it will speed up my code a bit .. gonna try it.

I have to say, i start to love the Padauks. They are working as documented, a really good solution to professional challenges we face, and low price ..  Thanks a lot to the community to have brought the tools and support that far. I will contribute as i can.

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 15, 2022, 11:05:52 am
One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register.

Could you explain your observation a bit more in detail? I'm working on a cycle accurate emulator which also includes peripherals (parts of it been used in the noiseplug showcase project: https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation (https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation))

You say the assembly code of

set1 PA,#0

will in fact read complete PA (to where), set the bit and then write it back (all in 1 cycle)?

How / what did you observe that lets you assume this?


Or do you mean that the SDCC C compiler might produce 3 opcodes (read, modify, write) for C code like "PA = PA | 1"?


JS

Edit:
When I look at the functional block diagram for IO pins in the datasheet (e.g. page 56 / Fig. 17:  http://www.padauk.com.tw/upload/doc/PFS122%20datasheet_EN_V001_20220518.pdf (http://www.padauk.com.tw/upload/doc/PFS122%20datasheet_EN_V001_20220518.pdf)) I assume, that a bit set instruction ( set1 )

I assume that the IC will only:

- set the "1" for the bit to set on the data bus
- activates the "WR data latch" line so the output data latch (flip flop) for the desired bit (pin) updates the value

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 21, 2022, 12:22:50 am
sorry for the delay.
compiler: it will definitely not do the read/modify/write as 3 opcodes, that you would see in the assembly listing and the set0.io instruction is actually assembly already.

i agree you would wish that only one bit would be changed, but this not what i observe.
There is a simple test to do:

add a pull-up (or program a pull-up) on one bit on PA or PB (lets take the example here, PB0).
i want to use PB0 as 'open collector' output (actually for i2c ..)
So i do a set0.io  PB,#0   - to set the bit to 0
after that, using PBC i can make the pin either '1' (due to the pullup) if i configure it as input, or '0' if i configure it as output in PBC.

then, while the bit is 'input', set ANY other bit in PB, one or zero does not matter.
the data bit '0' stored in the holding register for PB0 will be changed to a one, although no-one does a set1.io PB,#0

So it seems setting ANY bit in PB will 'read back' ALL values as seen from the port, change the one bit in question, and write them all to the port's holding register.
In normal situations (where inputs are inputs always) this would not harm as the value in the holding register is not important. however, in my usecase i depend on the 0 to be there, and as it is magically 'changed' now i need to set it to 0 everytime before i enable the output .. doable but annoying and i think its worth a warning.

By the way - i tried the 'undocumented' 16Mhz feature on the PFC154, works well, but it does not work on the PFC232. The PFC232 will not run with that clock option.

Johannes

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on December 21, 2022, 11:17:17 pm
Hello all,

It's been a while, but I just updated the pdk-includes repo with support for a bunch of additional ICs:
- PFC151
- PFC154
- PFC161
- PMS150G/PMS15B

I also added aliases for:
- PFS121, PFS122 (same as PFS172)
- PFS123 (same as PFS173)

This includes a few new peripherals as well:
- Touch (PFC161)
- LVD - Low Voltage Detector (PFC151, PFC161)
- RFC - (Undocumented) Resistance to Frequency Converter (PFC154, PFS154, PFS173)

I also enabled the Undocumented 11-bit ADC for PFS173.

This should bring pdk-includes up to par with all the ICs that the easy-pdk-programmer has include files for (in the development branch)... except for PFC232.

All the changes are currently in the 'new-ics' branch: https://github.com/free-pdk/pdk-includes/tree/new-ics
Pull Request (to capture any discussion) here: https://github.com/free-pdk/pdk-includes/pull/13

I don't have any of these ICs myself, so I can't do any actual testing, but the changes were fairly straightforward so I assume things will mostly work.  I'll merge these changes up to master after waiting a bit for feedback, and after doing some additional testing to make sure I didn't break anything else.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: serisman on December 21, 2022, 11:40:53 pm
In case anyone is interested...

I finally published a new version of my PDK Continuity Tester (https://github.com/serisman/pdk-continuity-tester) that solves an issue that was raised a while ago, and uses a better form factor.

I also finally published a simple PDK based Logic Probe (https://github.com/serisman/pdk-logic-probe) that can be a useful tool for breadboarding or troubleshooting.

Enjoy!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on December 24, 2022, 06:17:29 am
One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register.

Could you explain your observation a bit more in detail? I'm working on a cycle accurate emulator which also includes peripherals (parts of it been used in the noiseplug showcase project: https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation (https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation))

Would it make sense to merge this work into the uCsim simulators that SDCC uses?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on December 27, 2022, 11:51:09 pm
All, PFS132 is available, seems to be a 'better' PFS122 with improved (not R-Type) 12 bit ADC.

I am going to purchase a large number of those directly in China (somewhere between 10k and 100k pcs, i will stock them for longer term use in Europe for us), if some of you want some for testing, play projects etc, you can contact me with PM and i can send you some early next year (we should get them before Chinese New Year).
PFS132-S16A to be exact, SOIC-16 case.

Cheers

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 28, 2022, 05:54:18 pm
sorry for the delay.
compiler: it will definitely not do the read/modify/write as 3 opcodes, that you would see in the assembly listing and the set0.io instruction is actually assembly already.

i agree you would wish that only one bit would be changed, but this not what i observe.
There is a simple test to do:

add a pull-up (or program a pull-up) on one bit on PA or PB (lets take the example here, PB0).
i want to use PB0 as 'open collector' output (actually for i2c ..)
So i do a set0.io  PB,#0   - to set the bit to 0
after that, using PBC i can make the pin either '1' (due to the pullup) if i configure it as input, or '0' if i configure it as output in PBC.

then, while the bit is 'input', set ANY other bit in PB, one or zero does not matter.
the data bit '0' stored in the holding register for PB0 will be changed to a one, although no-one does a set1.io PB,#0

So it seems setting ANY bit in PB will 'read back' ALL values as seen from the port, change the one bit in question, and write them all to the port's holding register.
In normal situations (where inputs are inputs always) this would not harm as the value in the holding register is not important. however, in my usecase i depend on the 0 to be there, and as it is magically 'changed' now i need to set it to 0 everytime before i enable the output .. doable but annoying and i think its worth a warning.

Johannes

Actually it looks more like flipping the state of "PAC" / "PBC" from input to output might transfer the content of the input to the output latch...
I need to investigate more... So setting a bit seems to cause the port to also update all inputs... (unfortunately we can not see this from the diagram in PADAUK manual)

But I think you can prevent this easily. Just have a look at "PADIER" / "PBDIER"...
Here you can detach the digital pin input completely (again, have a look at  page 56 / Fig. 17:  http://www.padauk.com.tw/upload/doc/PFS122%20datasheet_EN_V001_20220518.pdf (http://www.padauk.com.tw/upload/doc/PFS122%20datasheet_EN_V001_20220518.pdf)) 
Setting the bit to 0 for a pin should make it impossible to "read back" anything from the actual port.

JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on December 28, 2022, 06:05:44 pm
One problem i stumbled upon which i would like to 'warn' about ;)
The bit set/reset instructions on the IO ports (PA and PB) do not affect a single bit. the implementation in the padauk is made in a way that they read back all 8 bits, modify the specific bit, and then put them back into the output register.

Could you explain your observation a bit more in detail? I'm working on a cycle accurate emulator which also includes peripherals (parts of it been used in the noiseplug showcase project: https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation (https://github.com/free-pdk/easy-pdk-showcase-projects/tree/master/noiseplug/emulation))

Would it make sense to merge this work into the uCsim simulators that SDCC uses?

uCsim is a different "beast" which I have not much knowledge of.

The emulator I'm working on is for realtime simulations with built in emulation of external components like PWM output routed to WAV output, WS2812B RGB led matrix to SDL2 drawing, ...


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: LovelyA72 on January 16, 2023, 10:22:00 pm
I think it will be nice to update the site for newer ICs.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vic_luga on January 30, 2023, 10:19:37 am
Hello. What could be the problem?
It is calibrated normally at 8 MHz

e:\easy-pdk-programmer-software>easypdkprog.exe write -npfc161  E:\easy-pdk-programmer-software\Examples\src\build\comptest_pfc161.ihx
Erasing IC... done.
Writing IC (394 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 5.00V ... calibration result: 892003Hz (0x8F)  out of range.
ERROR: Calibration failed
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 01, 2023, 03:34:40 pm
Hi,

according to your output:

Calibrating IC
* IHRC SYSCLK=1000000Hz @ 5.00V ... calibration result: 892003Hz (0x8F)  out of range.


you try to calibrate to 1 MHz (1.000.000 Hz).

In case you selected an 8MHz clock (like you wrote) then you get this error since calibration can only tune the frequency so slightly.

Solution: Either select a clock of 1MHz in your code if you want to calibrate to 1MHz or select calibrate to 8MHz (8000000) in case you wanted and selected an 8MHz clock in your code.


JS
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vic_luga on February 02, 2023, 02:42:04 am
Not so. When setting 8 MHz, calibration is normal.
If I install any other it is not calibrated. In this case, the file from the example, I did not change it.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: js_12345678_55AA on February 03, 2023, 10:06:38 am
Not so. When setting 8 MHz, calibration is normal.
If I install any other it is not calibrated. In this case, the file from the example, I did not change it.

Just tried it and it works without any issue:

8MHz:

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_8MHZ();                //use 8MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(8000000,4000);        //tune SYSCLK to 8MHz @ 4.000V
  return 0;                                     //perform normal initialization
}



./easypdkprog write -npfc161 build/helloworld_pfc161.ihx
Erasing IC... done.
Writing IC (184 words)... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 4.00V ... calibration result: 7973105Hz (0x50)  done.


1MHz:

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_1MHZ();                //use 1MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(1000000,4000);        //tune SYSCLK to 1MHz @ 4.000V
  return 0;                                     //perform normal initialization
}


./easypdkprog write -npfc161 build/helloworld_pfc161.ihx
Erasing IC... done.
Writing IC (182 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 4.00V ... calibration result: 997843Hz (0x50)  done.


For completeness, I just flashed the "comptest_pfc161.ihx" from the project:

./easypdkprog -nPFC161 write Examples/comptest_pfc161.ihx
Erasing IC... done.
Writing IC (394 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 5.00V ... calibration result: 998690Hz (0x50)  done.



Other possible problems:
* IC might be bad
* wiring to IC is not good
* clock selection is wrong in your code
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: vic_luga on February 05, 2023, 09:25:39 am
8MHz
E:\easy-pdk-programmer-software>easypdkprog.exe write -npfc161  E:\easy-pdk-programmer-software\Examples\src\build\helloworld_pfc161.ihx
Erasing IC... done.
Writing IC (184 words)... done.
Calibrating IC
* IHRC SYSCLK=8000000Hz @ 4.00V ... calibration result: 7945630Hz (0x7B)  done.

1MHz
E:\easy-pdk-programmer-software>easypdkprog.exe write -npfc161  E:\easy-pdk-programmer-software\Examples\src\build\comptest_pfc161.ihx
Erasing IC... done.
Writing IC (394 words)... done.
Calibrating IC
* IHRC SYSCLK=1000000Hz @ 5.00V ... calibration result: 786982Hz (0x29)  out of range.
ERROR: Calibration failed



Example code

// COMPARATOR test. VDD estimation using internal VBandGap (1.2V) reference, serial output of comparator results on PA7 at 19200 baud.
//
// We use 1MHz as sysclock so we can test with much lower VDD:
//
//  easypdkprog start --runvdd=5.0
//  easypdkprog start --runvdd=3.3
//  easypdkprog start --runvdd=2.0

#include <stdint.h>
#include <stdio.h>
#include "easypdk/pdk.h"

volatile uint16_t txdata;                       //txdata, serial data shift register

void interrupt(void) __interrupt(0)
{
  if( INTRQ & INTRQ_TM2 )                       //TM2 interrupt request?
  {
    INTRQ &= ~INTRQ_TM2;                        //mark TM2 interrupt request processed
    if( txdata )                                //txdata contains bits to send?
    {
      if( txdata&1 )                            //check bit (1/0) for sending
        __set1io( PA, 7 );                      //send 1 on PA7
      else
        __set0io( PA, 7 );                      //send 0 on PA7
      txdata >>= 1;                             //shift txdata
    }
  }
}

int putchar(int c)
{
  while(txdata);                                //wait for completion of previous transmission
  INTEN &= ~INTEN_TM2;                          //disable TM2 (setup of 16 bit value txdata is non atomic)
  txdata = (c << 1) | 0x200;                    //setup txdata with start and stop bit
  INTEN |= INTEN_TM2;                           //enable TM2
  return (c);
}

unsigned char _sdcc_external_startup(void)
{
  EASY_PDK_INIT_SYSCLOCK_1MHZ();                //use 1MHz sysclock
  EASY_PDK_CALIBRATE_IHRC(1000000,5000);        //tune SYSCLK to 1MHz @ 5.000V
  EASY_PDK_USE_FACTORY_BGTR();                  //use factory BandGap tuning value (tuned @ 5.0V)
  return 0;                                     //perform normal initialization
}

void main(void)
{
  //setup timer2 (TM2) interrupt for 19200 baud
  TM2C = TM2C_CLK_IHRC;                         //use IHRC -> 16 Mhz
  TM2S = TM2S_PRESCALE_NONE | TM2S_SCALE_DIV8;  //no prescale, scale 8 ~> 2MHz
  TM2B = 104;                                   //divide by 104 ~> 19230 Hz (apx. 19200)

  PAC = 0x80;                                   //enable PA.7 as output
  txdata = 0xD55F;                              //setup 2 stop bits, 0x55 char for autobaud, 1 start bit, 5 stop bits
  INTEN = INTEN_TM2;                            //enable TM2 interrupt, send out initial stop bits and autobaud char
  __engint();                                   //enable global interrupts

  //comparator VBandGap / VInt (case 3: VDD = [ 40 / (N+9) ] * 1.20 V ;
  static const char vddcompstr[16][5] = {"5.33","4.80","4.36","4.00","3.69","3.43","3.20","3.00","2.82","2.67","2.53","2.40","2.29","2.18","2.09","2.00"};

  //setup COMPARATOR: IN- = VBandGap, IN+ = VInt (selected by GPCS)
  GPCC = GPCC_COMP_ENABLE | GPCC_COMP_MINUS_BANDGAP_1V2 | GPCC_COMP_PLUS_VINT_R;

  for(;;)
  {
    puts("VDD is:");
    for( uint8_t n=0; n<16; n++ )               //loop over all 16 values of the VInt_R resistor ladder
    {
      GPCS = GPCS_COMP_CASE3 | n;               //case 3 covers 2.0V - 5.33V
      for(uint32_t d=100; d>0; d--);            //small delay after GPCS setup required

      if( GPCC & GPCC_COMP_RESULT_POSITIV )     //test if comparator result is positiv
        putchar('>');
      else
        putchar('<');

      puts(vddcompstr[n]);                      //output the coresponding VDD value (we use a string table to avoid printf)
    }

    for(uint32_t i=180000; i>0; i--);           //wait approx. 3s
  }
}
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on February 17, 2023, 01:16:40 pm
Hello All,

my wishful thinking that the PFS132 is 'just' the same like a PFS122 or PFS172 with better A/D peripheral did not realise well.

I have PFS132 on a board for testing but the programmer does not recognize it (obviously), it has a different chip id (0x764) and when i try to handle it with the PFS172 settings it fails.

Difference in the datasheets i see is that it has also 3x 11bit PWM and 8x8 multiplier, so it is a different animal than the PFS122.

Is there a chance to get it supported by the programmer ? I can send chips to whoever wants to try to make this work, i can also test settings and recompile the easypdkprog code if you have ideas what i should try.
The 'probe' shows VPP 4.5V VDD 2.0V ..

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on February 25, 2023, 11:06:35 am
Hmm no-one on the PFS132 ?  Anything i could try to see how to support it ? Anyone wants some to try ?

I have a quite large stock of PFS132 and just ordered PFS122 in large quantities (at 100k pcs the SO-16 is 0.04$ in china ..) now as they work as expected.

My current quest is to make a POE signature controller out of the PFS122 for both 802.3at and 802.3afn - this will allow you make a low cost solution to connect, for example, LEDs, directly to PoE.
If anyone is interested PM me.
Next quest will be to try to use the PFS122/132 as a switching power supply controller ...
Why do i do these things ?

PoE is everywhere, but the choice and availability of inexpensive, standards compliant PoE signature chips is limited, and those chinese companies who make PoE modules do not test and design well, deliver nonworking and bad product etc. Reputable module manufacturers like Silvertel are better but still there are a lot of caveats. If my project works (and i have first success already) i get a very intelligent, software programmable solution at a much lower cost.

Cheers

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on May 18, 2023, 12:18:46 am
Hi all, anyone volunteering to help adding PFS132 to the programmer/toolchain ?
Happy to invest some time but i need to understand how to do it ..

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: crossbound on June 26, 2023, 01:59:45 am
Hello everyone. Just trying to get my feet wet with the Padauk MCU's. Had a quick silly question regarding the LED's on the programmer. I don't seem to be able to figure out what each of the three LED's indicate. Searching the thread didn't seem to give me any results. Thanks for the info!
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: DC1MC on July 26, 2023, 11:07:09 am
If someone has a programmer compatible with PMC150 for sale in DE/EU kindly please contact me.

Cheers,
DC1MC
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: jacola on August 28, 2023, 09:44:28 pm
well, pretty much quiet here .. seems padauks are not in favor any more ;)
I have put out a 500$ bounty for the PFS132 support ..

https://app.bountysource.com/issues/123829632-pfs132-support (https://app.bountysource.com/issues/123829632-pfs132-support)

Cheers

Johannes
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 29, 2023, 04:59:11 am
Seems that Padauk is realigning their strategy:

https://www.digitimes.com/news/a20230814PD207/consumer-electronics-mcu.html (https://www.digitimes.com/news/a20230814PD207/consumer-electronics-mcu.html)

Could mean that they are looking into more complex and/or very specialized products. In any case, there seems to be reduced focus on ultra-low-cost MCU.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 29, 2023, 05:08:54 am
well, pretty much quiet here .. seems padauks are not in favor any more ;)
I have put out a 500$ bounty for the PFS132 support ..

https://app.bountysource.com/issues/123829632-pfs132-support (https://app.bountysource.com/issues/123829632-pfs132-support)

Cheers

Johannes

It seems the PFS123 is a direct replacement for the discontinued PFS173, but with a capacitance based ADC instead of resistor based. PFS173 is already supported. The amount of memory and periphery seems to be basically the same.

The section in the datasheet about the programming is identical for both devices. I'd guess there is a high likelyhood that the programming algorithm is the dame for both devices and only the deviceid needs to be changed. Have you already tried something in that direction.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on August 29, 2023, 05:24:30 am
Ok, i realized you were asking for PFS132, not PFS123.

The PFS132 is indeed a bit different, although the programming instructions are the same as for PFS123/PFS173. Possibly using the PFS173 programming algorithm still works when changing chipid and adjusting for different memory size?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: crossbound on October 17, 2023, 01:49:45 am
Just my little contribution at this time. I have been working on a breakout board and programmer riser design for the EasyPDK programmer. The breakout board features a pad on the bottom side for a decoupling capacitor and the top has a place for an LED and current limiting resistor connected to PA4. Pads are designed in such a way that 1206, 0805, or 0603 components can be used.
There will be two different versions of the gerber files, one that has a single board and riser, the other is panelized with mouse bites that will yield 15 breakout boards and 5 risers per panel. Dimensions of the panel is such that it will allow for ordering 5 panels for $2 on JLCPCB.
If anyone is interested I'll upload the gerbers to Github. Will be ordering a set for myself soon to verify.

(https://i.imgur.com/Qz4kqn8.png)
(https://i.imgur.com/guhn9jO.png)
(https://i.imgur.com/gGbEXfi.png)
(https://i.imgur.com/pvhO3WT.png)

(https://i.imgur.com/r8sRjQ1.png)
(https://i.imgur.com/KQsdtLj.png)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: tim_ on October 17, 2023, 05:08:39 am
Looks really neat! 0'1" less wide and you would not need the riser. :) But then, no place for silk screen...

Btw, which PCB layout program did you use?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: crossbound on October 17, 2023, 02:50:33 pm
Thank you.. I tried getting the header closer in to avoid using a riser, but unfortunately they would end up touching the pads for the MCU..  :--
Kicad is my software of choice. I did play around with EasyEDA, but it was not for me. I do however like the integration with LCSC for picking the parts.

Looks really neat! 0'1" less wide and you would not need the riser. :) But then, no place for silk screen...

Btw, which PCB layout program did you use?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on January 10, 2024, 04:42:52 pm
Can anyone give me some insight into how the 16-bit timer on Padauk MCUs works?

What I want to do is create a timeout timer of around 500 msec. I've figured I can do this by setting the T16 clock source to SYSCLK (which will be IHRC/16 = 1 MHz), dividing by 16 for 62.5 kHz tick rate, then setting the interrupt source to be bit 15 of the counter (count of 32,768). This should give me a timeout period of approximately 524 msec, which is good enough for my purposes.

But, I only want to enable this timeout timer on-demand, and wait for either an I/O pin to toggle or the timeout to expire (i.e. I don't want something to repeat every 500 msec).

I'm thinking there's two potential ways I can go about this. When I want to start the timeout, I could either:

- Reset the timer counter to zero, then enable the interrupt for T16 (INTEN |= INTEN_T16). Disable the interrupt at all other times.
- Enable T16 by setting its clock source, hopefully the counter is reset to zero whenever the timer is re-enabled. Keep T16 disabled (i.e. T16M_CLK_DISABLE) at all other times. Interrupt is enabled at all times.

The first method is difficult because the T16 counter can only be written or read with specific assembly instructions, STT16 and LDT16, and these instructions only read/write from/to a fixed memory address. To reset the counter to zero, I would have to do something like declare a global variable with a value of zero, then use inline assembly to write that value to the counter.

Code: [Select]
static uint16_t t16_reset_val = 0;

/* Wherever I need to reset T16 counter: */
__asm__("stt16 _t16_reset_val\n");

Also, the Free-PDK website detailing the PDK13 instruction set (https://free-pdk.github.io/instruction-sets/PDK13) says that the memory address for STT16 and LDT16 must be word-aligned. I don't know how to ensure that with SDCC, or if it's even possible.

The second method, I don't know if the counter value gets reset whenever the T16 is disabled/enabled. If it does, this approach would work, but if not it's not viable. Anyone know?
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 12, 2024, 08:57:59 am
If you want to set the timer to 0, why not just do so?

Code: [Select]
__sfr16 timercnt;

void f(void)
{
timercnt = 0;
}

SDCC doesn't have much support for alignment yet, and support for the 16-bit timer is quite incomplete (some stuff, in particular setting the counter to a small value, works), but it should always either generate correct code or give an error message.

Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on January 12, 2024, 05:31:29 pm
If you want to set the timer to 0, why not just do so?

Haha, yeah, I subsequently found that myself just yesterday. ;D

I previously saw the definition for T16C in the Free-PDK headers for a __sfr16 but with no address (i.e. no __at()) and thought that was odd and perhaps some vestigial thing. But then I found it is actually used in some example code (https://github.com/free-pdk/free-pdk-examples/blob/ea9d5021019d6910c9a365b66cd91676e504287b/include/millis.h#L16). I couldn't comprehend how that worked, so I went looking in the SDCC code for how the stt16 instruction was emitted.

Am I interpreting this code (https://sourceforge.net/p/sdcc/code/HEAD/tree/trunk/sdcc/src/pdk/gen.c#l1081) correctly, or is SDCC hard-coded to handle this specially? Does it just assume that any assignment of a literal value to any __sfr16 should be translated to a stt16 instruction loading from pseudo-register p? That seems a bit of a hack... :P I suppose technically there are no 16-bit peripheral or CPU registers, so this is a fairly safe assumption to make, but what happens if someone attempts to use __sfr16 to access a contiguous pair of high/low registers on a peripheral (e.g. PWM generator)?

(some stuff, in particular setting the counter to a small value, works)

Yes, I note that it only works assigning values 0-255, which is unfortunate, because I need to assign a value greater than that. :( Will still need to use the global variable method. Or maybe I will try writing some inline assembly to use p, given that is implicitly guaranteed to be at a word-aligned address.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on January 12, 2024, 07:42:35 pm
Yes, the 16-bit timer counter is the only 16-bit I/O location, so _sfr16 is considered to always mean the 16-bit timer counter.

The pseudoregister p is used as an 8-bit register followed by a 0x00 byte. So it cannot be used to write values larger than 255.
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on January 14, 2024, 06:57:45 pm
Anybody got any idea what's up with this Padauk app note (http://www.padauk.com.tw//upload/ApplicationNote/PMC-APN016_PMS150G_Writing_Guide_EN_20201225.pdf) regarding programming of PMS150G chips?

It seems like they're saying that for the PMS150G you need to add a 100 ohm resistor in series between the chip and the programmer on the PA5 line. They detail bodging some kind of adapter board that plugs in to a header on the back of the official Padauk programmer (and indeed, the latest versions of which apparently come with a proper adapter).

Does this seem like it would be applicable or necessary for programming the PMS150G with the Easy-PDK programmer?

I think they're just trying to add some over-voltage transient suppression to avoid damage to the IC when used in automated programming machines with long wires running from the programmer, because I think as PA5 is the VPP pin, it has no upper input protection diode. Indeed, even in the datasheet they say "Please put 33Ω resistor in series to have high noise immunity when this pin is in input mode".
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: HwAoRrDk on January 22, 2024, 08:10:16 am
Frustratingly, the latest released binaries of the Easy-PDK programmer software on the GitHub repository are only for the older v1.3, so they are missing support for many more recent Padauk MCU models (e.g. PMS150G). Support for these have only been added in the "development" branch of the software (which is essentially v1.4), so if you want that you have to build the software yourself. :(

I wanted to build the Windows binary, but for most *nix-centric software actually doing so on Windows itself is usually a clusterfuck (authors typically expect an environment with all sorts of nonsense like cygwin, msys, etc.), so it's nearly always much, much easier to cross-compile on Linux.

In case anyone else at some point wants to do the same, I figured out how:

1. Download (and unzip) or Git clone the "development" branch: https://github.com/free-pdk/easy-pdk-programmer-software/tree/development
2. If not already available, install the MinGW development tools (e.g. sudo apt-get install mingw-w64 on a Debian-based system).
3. Build the included argp-standalone library (from within lib/argp-standalone-1.3 folder): ./configure --host=x86_64-w64-mingw32 CFLAGS='-w -Os' && make
4. Finally, build easypdkprog: make CC=x86_64-w64-mingw32-gcc EPDKVER=1.4 ECFLAGS=-Ilib/argp-standalone-1.3 ARGPSALIB=lib/argp-standalone-1.3/libargp.a EXE_EXTENSION=.exe

:-+
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: KaeTo on February 18, 2024, 01:39:31 pm
Hello,

I have a problem with the PMS150C regarding the bandgap. Maybe somebody here can help me or at least verify my observed behavior.
When I do the bandgap calibration for PMS150C-SO8 everything is okay. I get a calibration result != 0 and the bandgap behaves as expected. When I use my PMS150C-U6 chips I get a result of 0x00 and the bandgap is way of. Has anyone else seen this behavior with the U6 (SOT23-6) variant or could verify it, if you get the same calibration result.
At the moment my suggestion would be, that I got a bad batch.

Thank you :)
Title: Re: EEVblog #1144 - Padauk Programmer Reverse Engineering
Post by: spth on March 11, 2024, 07:53:57 am
Padauk has been discontinuing and introducing devices, and the free programmer hasn't gotten support for new devices in a while.
How can we restart the process of getting support for more devices? Is anyone with experience in adding support for additional devices still active?