Rockbox.org home
releases
current build
extras manual
wiki
index mailing lists
IRC
forums bugs
patches
 requests



TWiki > Main > CreativeZVMPort
Main . { Users | Groups | Changes | Index | Search | Go }

Rockbox the Creative Zen Vision:M

About

Watch the ZVM Port Thread and FS#8686

Port Status

  • The LCD driver works
  • The button driver works, but there hasn't been a polling-method implemented; currently it is only interrupt based
  • The ATA driver works
  • The I˛C(Inter-Integrated Circuit) driver works
  • The SPI(Serial Port Interface) driver should work, but is untested
  • The UART(Universal Asynchronous Receiver/Transmitter) driver should work, but is untested
  • The USB driver works partly(EP0SETUP is received!), but there's something wrong with the interrupts
  • System rebooting works (3/4 of the times)

Install method

WARNING: this is only for people who know what they're doing, don't try this if you don't understand the consequences!
WARNING: this will format your player and you will lose all your data!

To people who want to replicate my case this is what you got to do:

  • you've got to mount your ZVM's HDD to your computer (using an 1,8"->3,5" adapter or other method) and format the second partition (starting at byte 0x3200200) as a FAT file system -> to do so (on Linux):
losetup -o 52429312 /dev/loop0 /dev/XXX
mkfs.vfat -F 32 /dev/loop0
mount -t vfat /dev/loop0 /mnt/XXX
  • set up a Rockbox build environment and check out latest SVN (HINT: use the VMWare image)
  • mount the FAT partition you've created in step 1 (see last line) and copy all files from ./rockbox/* to /mnt/XXX/.rockbox/ (except for rockbox.zvm)
  • use either utils/MTP/sendfirm or an other MTP utility (CreativeWizard) to upload the firmware (rockbox.zvm)

Information about the ZVM 30GB

Pictures/scans

Internal components

Component Info Driver in Rockbox? 30GB/60GB
TI TMS320DM320 Dual Core ARM9/C5409 DSP System On Chip - ARM926EJ-S product specs & datasheet partially Both
Spansion S29GL032M 4MB (=32Mb) flash memory / Both
Infineon HYB 25L256160AF-7.5 (x2) total of 64MB RAM: product is discontinued / Both
Philips ISP1583BS USB 2.0/ATA (IDE) controller ISP1582 driver is present 30GB
Philips ISP1761ET USB 2.0(OTG/Client) / ATA (IDE) controller
Linux Host and Device driver
ISP1582 driver is present, compatibility unknown 60GB
Toshiba MK3006GAL (and this)
Hitachi C4k60 (pdf)
The Hitachi appears to be a zif connector while the Toshiba is an IDE / Both
Samsung LTV250QV-F02 LCD has quite a few numbers on it: V250QVF02S6516J12, USP5280371, GA060525 AO, DA060124BC.
Similar used in the Cowon D2
partially Both
SKC LPCS285385 battery rated at 1250mAH at 3.7v / 30GB
TEA5761UK (datasheet) FM Radio TEA5767 is supported Both (oddly)
Microchip PIC18LF4320 Microcontroller, used for dock, buttons, etc
Compatible compiler
no Both
TI TLV320AIC23BZ (datasheet) Stereo Audio CODEC, 8-to 96-KHz, With Integrated Headphone Amplifier yes Both
RTC This component hasn't been identified yet no Both
lLC08A Quadruple 2-input positive-AND gate / Both
LW053A Triple 2-channel CMOS analog multiplexers/demultiplexers
(located right of onboard flash [possibly TV out])
/ Both
TI CN211 24 - bit low voltage switch bus / Both
Linear Technology LTC3455 (datasheet) Dual DC/DC Converter with USB Power Manager and Li-Ion Battery Charger no Both
The 60GB contains almost exactly the same components, only (currently known of) difference is the USB chip.

How internals are connected

DM320:
  • I˛C
    • PIC (at 0x07)
    • TLV320 (at 0x1A? unverified)
    • TEA5761UK (at 0x24? unverified)
    • RTC (at 0x51)
  • EMIF
    • HDD (at 0x50FEE000)
    • Unknown (at 0x50FFC000)
    • ISP1583 (at 0x60FFC000)
    • SDRAM Controller
      • 64MB Infineon RAM (at 0x00900000)
    • FLASH Memory Interface
      • 4MB Spansion flash memory (at 0x00100000)
  • SPI
    • LCD (slave select pin is BITSET2/CLR2 |= (1 << 5) )
  • UART
    • LCD doesn't seem to work if UART isn't enabled
  • GIO
    • GIO0 is used as an interrupt triggered by the PIC
    • GIO2 is used as an interrupt triggered by the HDD
    • GIO7 is used as an interrupt triggered by the ISP1583
    • GIO26, GIO34 is used as the Video Encoder clock
    • GIO29, GIO32, GIO36, GIO35, GIO37, GIO40 are related to the LCD
    • GIO3, GIO5, GIO14 are related to the ATA controller/HDD
TLV320:
  • Control
    • I˛C <= DM320
  • Audio
    • unknown <= TEA5761UK
    • DSP/I˛S mode <= C54xx DSP
PIC:
  • buttons
  • buttons backlight (unverified)
  • (piezo) clicker (unverified)
  • touchpad
  • headphones detection
  • dock connector
    • USB connector
    • power connector
    • TV out connector (unverified)
  • hold switch LED (unverified)
  • LCD backlight (unverified)
  • probably other stuff too...

Original Firmware

Firmware Info

The firmware used by Creative is Nucleus RTOS.
They use Nucleus PLUS and the ARM925 TI v. 1.14 toolchain to compile it according to strings found in FBOOT.
This is based on MicroWindows (Nano-X), as several assert messages are found pointing to (open source) source code. (even NeurosTechnology uses Nano-X)
Also libpng is incorporated (and zlib of course).

Other strings of companies working on the firmware:

  • Copyright MGC 2004 - Nucleus PLUS - ARM925 TI v. 1.14
  • Accelerated Technology Internal Use Only - Serial Number: NP0000
  • Copyright(c) Founder Corporation.2005

Modifying the firmware

Modifying the firmware is as easy as deleting a block/block data, inserting the new data, adjusting the Size attribute of the block and the CIFF block and computing the NULL checksum of the CIFF block (so without the NULL block).
You don't have to fill the entire firmware with all the blocks, if you for example just want to replace Hdeviceinfo.xml with another one, you only have to make a CIFF, CINF, DATA and NULL block (so you do not have to include all the others).

Another way is using CreativeWizard (Windows only and requires .NET 2.0).

Uploading a firmware

You can either compile the program located in utils/MTP/ in Rockbox SVN or you can get the hacked version of the official firmware updater.

Firmware Boot

  1. The built-in boot loader loads a limited sized secondary boot loader from a fixed location in flash memory to a fixed address.
  2. The secondary boot loader (named FBOOT in the firmware) decrypts and loads the Rescue Mode software (FRESC), also from flash memory.
  3. The Rescue Mode software decrypts, decompresses and loads the actual player software (CENC/TL) from a file named jukebox2.jrm on the HDD.
    If the validation checks fails or switch is hold to ON/OFF, it'll load a Rescue Mode menu, which allows you to "reload" the firmware amongst other things.
    1. Try opening jukebox2.jrm(load it into RAM, disable MMU and I/Dcache and jump to 0x1EE0000), if it fails show error and go to Rescue Mode
    2. Check the internal database if file type was ŠTL
      if(true): decrypt and decode and execute data
      else: show error and go to Rescue Mode
    3. Check the internal database if file type was CENC
      if(true): decode and execute data
      else: show error and go to Rescue Mode
    4. If file type is different: execute data
Note: prior to executing data, the first 4 bytes are checked if they match 'EDOC'; if check fails: show error and go to Rescue Mode.

The 'actual firmware loading' goes as follows:

  1. location 0x0 contains a jump to the reset vector
  2. the reset vector initializes the coprocessor and maps several memory addresses (including the USER DATA MAPPINGS; all of this isn't part of the Nucleus core)
    The mapping consist of these steps:
    1. there are 2 main variables in RAM (called mappings1 and mappings2 here);
      0x900000 is stored in mappings1 and (0x904000 | 0x13) in mappings2
    2. more info to come...
    3. USER_DATA (starts at 0x1C00004) is parsed as this:
      1. first 4 bytes are read into buffer (=length of data)
        if (buffer==NULL) return;
      2. next 4 bytes are read into second buffer (=address of data)
      3. if !(buffer2 & 3) { [copy data from (end of buffer2) to *(buffer2) for (buffer) bytes]; }
        else { buffer2-= 4; [copy data in pairs of 4 bytes from (end of buffer2) to *(buffer2) for (buffer) bytes]; }
      4. go back to step 1
  3. finally INC_INITIALIZE(first_available_memory); is called with first_available_memory pointing to the start of USER DATA MAPPINGS (=0x01C00000)
  4. INC_Initialize_State is set to INC_START_INITIALIZE and INC_INITIALIZE() initializes all basic Nucleus kernel entities
  5. Application_Initialize(first_available_memory); is called (this isn't part of the Nucleus core)
  6. INC_Initialize_State is set to INC_END_INITIALIZE and TCT_Schedule(); is called (starting the main Nucleus threading loop)

0x1EE0000

This is the FRESCUE structure parsing code, located at 0x228 in FBOOT in ZVM firmware.
It disables all caches and MMU and cleans it. Then it parses the loaded data (given by arguments R0->memory pointer and R1->size) and loads it into the corresponding memory addresses.
Several checksum checks are done (described at jukebox2.jrm) and if one fails, code jumps to an infinite loop.
After all loading is done, code jumps to 0x0.

Below is a C code example for loading a firmware image.

#define OF_firmware_load(mem_addr, size) asm volatile ( \
                                         "mov r1, %1\n" \
                                         "mov r0, %0\n" \
                                         "ldr pc, =0x1EE0000\n" \
                                         : \
                                         : "r"(mem_addr), "r"(size)\
                                         );
OF_firmware_load(ptr_to_loaded_image, size_of_loaded_image);

Upload Code To The Player

The code you want to upload should be raw binary, so no ELF format. Scramble is included in Rockbox SVN. If you run it like this:

scramble -creative=zvm inputfile outputfile
It will take a binary file and output a Rockbox compatible Hjukebox2.jrm wrapped up in a CIFF structure (meaning: Rockbox thinks it is loading from 0x900000 so the binary is loaded at that address and 0x0 contains MOV PC, 0x900000)

LCD info

The LCD is controlled via the serial interface of the TMS320 (a driver in Rockbox is present) and the built-in OSD facilities (serial is only LCD on/off).

Some uncategorized data:

raw dump of spi_send_block: http://pastecode.com/?show=f627241eb
analyzed version:

function spi_send_block(char arg_0, char arg_1) {
    IO_GIO_BITSET2 &= (1 << 0x5);
    spi_send_byte(0x74);
    spi_send_byte(0);
    spi_send_byte(arg_0 & 0xFF);
    spi_send_byte(0x25);
    IO_GIO_BITCLR2 &= (1 << 0x5);
    IO_GIO_BITSET2 &= (1 << 0x5);
    spi_send_byte(0x76);
    spi_send_byte( (arg_1 >> 8) & 0xFF);
    spi_send_byte(arg_1 & 0xFF);
    spi_send_byte(0x25);
    IO_GIO_BITCLR2 &= (1 << 0x5);
}

LCD init function: http://mcuelenaere.pastebin.com/f23b3226a

HDD partitioning info

The first sector consists of this structure:
struct partition_struct
{
    unsigned int end;
    unsigned int start;
    char name[8];
};

struct hdd_struct
{
    char MBLK[4];
    int block_size;
    long long total_disk_size;
    struct partition_struct minifs;
    struct partition_struct cfs;
};
A file header on the minifs partition consists of this (incomplete) structure stored at 0x144200 (= sector 0xA21):
struct __attribute__ ((aligned (32))) minifs_file
{
    char name[16];
    unsigned int unknown;
    unsigned int size;
    unsigned int index;
    unsigned int index2; /* The same as above */
};
There can be maximum 128 headers (so 32*128=0x1000 bytes)

Some interesting links:

Links are down, maybe archive.org has some remains.. BACKUP:

Notes:

  • The disk available in the Removable Drive option in the OF is stored as a file named VFSYS in the cfs partition. Currently it isn't possible to access it as the cfs nor the minifs file system has been figured out.
  • The minifs file system is supposedly based on BFS (not BeFS) which was called minifs in earlier days (now it is in the VSTa OS)
  • There is a disk dump available (see RAR comments for more info).

Firmware Format

010 Editor Template

Description

The firmware is Little Endian.

A firmware always starts with the ASCII string FFIC (=CIFF). Followed by the total size of the file minus the last (NULL) block and possible some padding bytes.
After this header comes a block structure, always started with a 4-byte string header (e.g. FNIC, ATAD, LLUN, CNEC, 0TXE or LTŠ). Then comes (again) the size of this block.
Then you have, based on the type of block: a) a data block with size of Size b) a 32-byte Unicode name(=filename) and the data block of (Size-32).

Overview table

Block Type Block Size Description Extra
FNIC 96 bytes player name (e.g. Creative Zen Vision:M) Unicode formatted
ATAD depends on Size attribute   if name starts with F->Flash, H->HDD
LLUN 20 bytes contains HMAC-SHA1 checksum of CIFF block  
CNEC/LTŠ depends on Size attribute encrypted player data(gets written to jukebox2.jrm on HDD) has no Description attribute
0TXE depends on Size attribute gets written to internal device (either mcu0 or ide0) name attribute is 24 bytes long

Normal files to be found in an official firmware

Block Type Name Information File Format
FINC n.a. player string  
ATAD FBOOT flash boot loader fboot_decrypt.cpp
ATAD FRESC flash rescue mode (key is 'Copyright (C) CTL. - zN0MAD iz v~p0wderful!')  
LTŠ n.a. hdd firmware file jukebox2.jrm
ATAD Hjukebox.grs graphics and other UI data jukebox.grs
ATAD Hjukebox2.jrs multilingual strings jukebox2.jrs
ATAD HCreative_T.TTF Unicode font  
ATAD HCreative_S.TTF Unicode font  
ATAD Hsplash.jbm hdd boot loader graphics JBM2
ATAD Hdevicon.ico icon used in MTP mode  
ATAD Hdevlogo.png picture of 'CreAtive'  
ATAD Hdeviceinfo.xml MTP description  
ATAD Hjukebox.opt player settings (only found in EU firmware -> EU volume cap is present in it)  
0TXE Pmcu0 (mcu0 = internal used name for the PIC) contains the binary code for the PIC EXT0
LLUN n.a. firmware checksum  

CINF block

The CINF block is the identifier of the firmware i.e. it says if the firmware belongs to a Creative ZVM 30/60GB, Creative ZEN, etc..
For example: the 30GB ZVM contains the Unicode string 'Creative Zen Vision:M' and the 60GB contains 'Creative Zen Vision:M Go!'.

NULL block

The NULL block in the current Creative ZVM's is a HMAC-SHA-1 computed checksum of the CIFF block using the key for your device.

ŠTL block

The ŠTL block gets written to the ZVM's HDD as jukebox2.jrm
It is encrypted using Blowfish in CBC mode with the key used for your device and after that you have to decompress/decode it using the CENC algorithm (described on DellDJPort).

EXT0 block

This contains the code uploaded to the PIC. The format is:
char header[4];
char padding[2];
unsigned char length_a;
unsigned char length_b;

total_size = (length_b + (length_a << 8) + 0xA) & 0xFFFF;

jukebox.opt file

This file contains the firmware's factory-set settings; like in the EU firmware it has VMX=0, which defines the EU volume cap. Based on firmware reverse engineering the player also accepts DBG=1 and FM=0.
Presumably the first one sets a debug flag (nothing notable happens, I've tested it myself) and the second one could disable the FM radio functionality (not tested).

jukebox2.jrm file

The format of this file is similar to the nk.bin format: it contains a main block (EDOC), 4 bytes long followed by a WORD which indicates the size of the file.
Then you have another WORD which has a currently unknown value (can be set at 0x0000 without problems).
After that you have an array of this type of struct:
typedef struct {
UINT Address;
UINT Length;
UINT Checksum;
UCHAR Data[Length];
} BLOCK;
Address is the physical address to which Data is loaded.
This array loops until the end of the CODE block.

The checksum is calculated as follows:

FSeek(0xC);
local int i = 0x239C;
local uint j = 0;
local uint temp = 0;
while(i>0){
   if(i<4) break;
   temp = ReadUInt(FTell()); //FTell() tells us the current stream position and ReadUInt() reads 4 bytes
   j += temp + (temp>>16);
   FSkip(4); //FSkip() skips x bytes in the stream (ReadUInt() doesn't move the pointer)
   i -= 4;
   if(i<4) break;
   temp = ReadUInt(FTell());
   j += temp + (temp>>16);
   FSkip(4);
   i -= 4;
   if(i<4) break;
   temp = ReadUInt(FTell());
   j += temp + (temp>>16);
   FSkip(4);
   i -= 4;
   if(i<4) break;
   temp = ReadUInt(FTell());
   j += temp + (temp>>16);
   FSkip(4);
   i-= 4;
}
j = j << 16;
Printf("%x", j);

At the end of the file you have another block (NULL) - the header is also 4 bytes long - followed by the size in WORD format (which is always 20 bytes) and then (presumed) a SHA-1-HMAC hash of the CODE block; although the key hasn't been found yet; but the device seems to ignore this block if it isn't present.

Flash files

The format used is unknown, as no flash dumps yet are available and no reverse engineering has been done to find this.
What is presumed, is that following files are on the flash chip:
  • BOOT: contains Nucleus kernel + custom software; loads RESC; can be identified by the 'CreAtive' splash screen; contains encrypted data starting at 0xB000: RSA encrypted with 128-byte public key located at 0x410; view fboot_decrypt.cpp code for more info
  • RESC: structure is the same as jukebox2.jrm; contains Nucleus kernel + custom software; loads jukebox2.jrm; can be identified by the 'ZEN' splash screen
  • TSIG
  • CONF
  • TOC0 (not sure)
  • PFM1 (not sure)

Other Creative players' firmware information

Since these information about the firmware applies to (almost?) the whole Creative Zen line, you'll find here some info for other players (like NULL block key, CINF header, ŠTL block key, ...)

Player CINF NULL key ŠTL
Creative Zen Vision:M Creative Zen Vision:M CTL:N0MAD|PDE0.DPMP. 1sN0TM3D az u~may th1nk*Creative Zen Vision:M
Creative Zen Vision:M 60GB Creative Zen Vision:M Go! CTL:N0MAD|PDE0.DPMP. 1sN0TM3D az u~may th1nk*Creative ZEN Vision:M (DVP-HD0004)
Creative ZEN Creative ZEN CTL:Z3N07|PDE0.DPMP. 1sN0TM3D az u~may th1nk*Creative ZEN
Creative Zen Vision Creative Zen Vision ŠTL CTL:N0MAD|PDE0.DPMP. 1sN0TM3D az u~may th1nk*Creative Zen Vision
Creative Zen Vision W Creative Zen Vision W CTL:N0MAD|PDE0.DPMP. 1sN0TM3D az u~may th1nk*Creative ZEN Vision W
Creative Zen Micro   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*Creative Zen Micro
Creative Zen MicroPhoto   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*Creative Zen MicroPhoto
Creative Zen Sleek   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*Creative Zen Sleek
Creative Zen Sleek Photo   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*Creative Zen Sleek Photo
Creative Zen Touch   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*Creative Zen Touch
Creative Zen Jukebox Xtra   CTL:N0MAD|PDE0.SIGN. 1sN0TM3D az u~may th1nk*NOMAD Jukebox Zen Xtra
Creative Zen V Creative ZEN V CTL:N0MAD|PDE0.DPFP. 1sN0TM3D az u~may th1nk*Creative ZEN V
Creative Zen V Plus Creative ZEN V Plus CTL:N0MAD|PDE0.DPFP. 1sN0TM3D az u~may th1nk*Creative ZEN V Plus
Creative Zen V Video Creative ZEN V (Video) CTL:N0MAD|PDE0.DPFP. 1sN0TM3D az u~may th1nk*Creative ZEN V (Video)

CreativeWizard

CreativeWizard is a .NET 2.0 application intended for analyzing and modifying Creative Zen firmwares. You can download it at epiZENter.
For creating a firmware, following steps are required:

  1. 'Make firmware'
  2. 'Select your player'
  3. choose your player from the list and press OK
  4. 'Add block'
  5. select the newly added block
  6. change type to 'DATA'
  7. check 'Use file instead of data'
  8. type 'Hjukebox2.jrm' in 'Filename' textarea
  9. choose the file
  10. press 'Create Firmware'
  11. press 'Yes'
  12. press 'OK'
  13. in main window: press 'Upload Firmware'
  14. choose your firmware and upload it to your player

External Links

Wiki Links


CategoryFrontpage: Creative Zen Vision:M Port Index [New Ports]

Attachment Action Size Date Who Comment
else ZVM-Blocks.bt manage 1.4 K 21 Nov 2007 - 17:28 MaurusCuelenaere 010 Editor block structure template
else ZVM-JBM2.bt manage 0.4 K 21 Nov 2007 - 17:29 MaurusCuelenaere 010 Editor Splash.jbm structure template
else ZVM-Jukebox-grs.bt manage 1.3 K 21 Nov 2007 - 17:30 MaurusCuelenaere 010 Editor Jukebox.grs structure template
else ZVM-Jukebox2-jrs.bt manage 1.3 K 21 Nov 2007 - 17:31 MaurusCuelenaere 010 Editor Jukebox2.jrs structure template
else ZVM-EXT0.bt manage 0.9 K 21 Nov 2007 - 17:32 MaurusCuelenaere 010 Editor EXT0 block structure template
zip zenutils.zip manage 649.4 K 02 Dec 2007 - 18:20 RasmusRy Utilities for working with zen firmwares
c fboot_decrypt.cpp manage 3.4 K 17 Feb 2008 - 11:10 MaurusCuelenaere FBOOT decryption code
else ZVM-Firm.bt manage 1.1 K 17 Feb 2008 - 12:06 MaurusCuelenaere 010 Editor Jukebox2.jrm structure template
else DiskDump.rar manage 87.8 K 20 Apr 2008 - 11:25 MaurusCuelenaere A diskdump of a freshly formatted Creative ZVM (see RAR comments for more info)
else Pmcu0.asm manage 205.9 K 23 Apr 2008 - 12:38 MaurusCuelenaere asm dump of the PIC's firmware

r131 - 06 May 2008 - 17:12:05 - MaurusCuelenaere
Edit | View raw | Attach | Ref-By | History: r131 < r130 < r129 < r128 < r127 | More | Refresh cache

Copyright © 1999-2008 by the contributing authors.