Archive for May, 2007

NDS Storage Devices

In the style of one of my bad habits, the too detailed essay writing has been in my drafts. So I’ve decide to discard it and writing from the scratch again, making things simpler and shorter. While this may leave out information or tacit details I know, I guess you could learn them from other sources or just ask from me.

On the topic, basically my views on the different storage devices for the DS- storing games, applications, music, homebrew, backups etc..

MK5
The first card I bought was Ultra N-Card, called UNC by my sellers. It was recommended by my friend, saying that it was “cheaper” as no external memory cards (CF, SD, Mini-SD…) and its card readers were needed. So the way of copying files in/out from the pc basically needs connecting using a USB via its slot-2 (GBA slot).

The downside:
Drains battery while transfering.
Slow transfer rate ~ 600kb/s

Now looking up this product on the net leads me to many other names DSLinker (classical to some china products), but its seems the best site for this card calls this MK5 GIGA Cart NAND Flash.

The OS on boot starts the fat system looks for all runnable applications in the card. This takes a considerable amount of time from ~15s depending on how packed is the card. The OS then shows a graphical screen with 2d/3d icons which you can select with the stylus (a plus point).

So far, common homebrew seems to run, but access to file system is only read-only due to their current DLDI support.

Regarding stability, I experienced hangs in games, crashes in the cards, corruption of fat system, which requires formating of the card. Until a point my card totally could not be recognised by the pc, I returned it to the shop.

So far, the plus points are that running it wouldn’t kill the battery much, and that the hope of developments in their firmware are active. I place only stuff I wouldn’t need transferring much in it.

My recommendation: Not really.

Supercard Lite
Due to the many break downs in my card, I decide to get a supercard, one of the reasons it could be used a “memory extension” and better homebrew support. I initially thought I would get a supercard rumble edition, but at least my seller (from supercard.sg, now closed) recommended the lite edition as the rumble edition as he said it was “bad design” I guess it didn’t contain the “ram” for GBA support.

So the sc lite uses a TF or a MicroSD card, and it goes into slot-2. Without patching the DS firmware, a slot-1 card called PassMe or SuperKey is needed to run DS applications from the GBA slot. So one of the downside is that battery drains quicker, either because the need to power slot 1& 2 and perhaps because of its “ram”.

Their OS boots quickly, but the interface for loading roms basically is a text-based menu, you navigation is by buttons without stylus. Backup roms would require you to use their software to patch before you can use them.

Homebrew support, without it, I wouldn’t consider buying this. So far, almost all applications seems to work for it (of course after patching with DLDI). Things that require quick transfer between my pc and the ds would go into my 1GB kingston micro-sd card. Pulling out and placing into my card reader ensures high speed transfer without draining my batter during transfer.

Recommendations: Not too bad.

Of course the 2 choices I had might and wouldn’t be the best for you. Infact there are other more attractive and advanced solutions around. I recommend you look at these few alternatives.

R4 - Slot 1, using micro-sd. Seems pretty good. Around about over a year..
M3 Solution - Slot 1 & 2. Slightly pricer if you want their support for movies, nes roms, gba..
upcomings:

Ninjapass Evolution X9 SLOT-1 Pretty good features too.
G6 Real DS flash - pretty attractive features.

Anyway here are the factors to look out if you are consider 1.
1. Reliability- to work and last
2. OS- Homebrew friendly? ROMs require patching? Customisable? Skinnable? ROM Compressions? Auto DLDI patcher? Does OS get supports and updates?
3. Type of storage device and the method of transfering.

Lastly, if storage device gave you the impression it was a physical storage device for ds, see this crystal casing

and rubber/silicon casing .

For mine? After testing out a couple of those nds casing protectors, I settled with this crystal case with silicon padding inside. A decision you might make for your phone or pda too..

Cycling to Pengerang’s Seafood Plan

12 May 2007 Plans
0500 Assemble, Equipment Check, Set off
0730 Changi Village, Meet up contacts
0800 Tugboat Journey to Pengerang
0900 Arrival at Pengelih Jetty, Start Journey to Town
1045 Rest and look around town
1100 Regroup and prepare for lunch
1300 Finish Lunch and Shopping
1500 Back to Johor Jetty
1600 Boat ride to Singapore
1700 Return trip to Sembawang
1930 Home Sweet Home!
2000 Dinner

Estimated Cycling Distance
Home -> Changi Jetty: 32km
Johor Jetty -> Seafood Restaurant: 16km
Total Distance: 48km x 2 = 96km

Preparation
-Study Maps
-Bag pack
-Rest

Equipments
-Bicycle
-Shoes
-Helmet
-Wallet
-Passport
-HP
-GPS receiver
-GPS Maps in Camera phone
-2-way radios
-Cycling Bag
-Water bag
-Clothes

Dictionary Browser Implemented!

I got some good news for the DictionaryForMIDs (the very cool dictionary/translator midlet for j2me compatible phones) community today. Basically its an implementation and integration of a FilePicker using codes borrowed from WTK examples and elsewhere.

Good news. I’ve got the browser implemented and working.

My next step will be the file decompression. I already have some J2SE codes to compress to an archive- we could use it to extra from old jars and place them in new files.

My current implementation I working with is tar with zlib compression. We might be able to implement zip/jar support, but I sort of given up on it at the moment. Infact, tar with zlib gives greater compression, although my guess is its slower.

File Picker

Compression in Java Implementation

Wanting to add zip/jar files on-the-fly decompression/reading implmentation for DictionaryForMids, I experimented classpath (A free/GNU replacement for Sun’s proprietary core Java class libraries)and jazzlib (A pure java implementation of the java.util.zip library) sources.

Even after I could make them compile, it seemed that some files couldn’t go through the preverifier (for unknown reasons, but i guess its some missing links or file size) so it couldn’t be packaged for mobile phones. [update] I managed to fix this problem by just looking at the errors when building the sources.

Frustrated, I look at some other alternatives.

TAR - A container file with no compression.
GZip - There are a few other implementations out there.
ZLib - I could use the files from JZLib re-implementation of zlib in pure Java..
BZip - I couldn’t find an implementation although there seemed to be from some time back.

Ideally, to get real compression, files would be tared first, then “hard” compressed at the next layer. Someone did a comparison of the different way of compression here. My tests show TAR and JZlib giving best compressions but the usual archivers (eg. Winrar, TUZip) do not open them. Tar with Gzip gives good storage for performances.

Take a look at my test codes for compressing files.

import java.io.*;
import java.util.zip.*;

public class Zip {
   static final int BUFFER = 2048;
   public static void main (String argv[]) {
      try {
         BufferedInputStream origin = null;
         FileOutputStream dest = new
           FileOutputStream("C:\\Users\\Zz85\\Desktop\\DictionaryProject\\test.zip");
         ZipOutputStream out = new ZipOutputStream(new
           BufferedOutputStream(dest));
         //out.setMethod(ZipOutputStream.DEFLATED);
         byte data[] = new byte[BUFFER];
         // get a list of files from current directory
         File f = new File("C:\\Users\\Zz85\\Desktop\\DictionaryProject\\Dictionary\\.");
         String files[] = f.list();

         for (int i=0; i < files .length; i++) {
            System.out.println("Adding: "+files[i]);
            FileInputStream fi = new
              FileInputStream(f.getParent() + "\\" + files[i]);
            origin = new
              BufferedInputStream(fi, BUFFER);
            ZipEntry entry = new ZipEntry(files[i]);
            out.putNextEntry(entry);
            int count;
            while((count = origin.read(data, 0,
              BUFFER)) != -1) {
               out.write(data, 0, count);
            }
            origin.close();
         }
         out.close();
      } catch(Exception e) {
         e.printStackTrace();
      }
   }
}

This is a classic way of compressing a folder (without its subdirectorie, but doable) to a zip file. The other methods are almost similar.


import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;

import com.ice.tar.TarEntry;
import com.ice.tar.TarOutputStream;
import com.jcraft.jzlib.JZlib;
import com.jcraft.jzlib.ZOutputStream;

public class PackDictTest {
	static final int BUFFER = 2048;
	   public static void main (String argv[]) {
	      try {
	         BufferedInputStream origin = null;
	         FileOutputStream dest = new
	           FileOutputStream("C:\\Users\\Zz85\\Desktop\\DictionaryProject\\test.tar.Z");
	         TarOutputStream out = new TarOutputStream(new
	        		 BufferedOutputStream(new ZOutputStream(dest,JZlib.Z_BEST_COMPRESSION)));
	        		//BufferedOutputStream(new GZIPOutputStream(dest)));
	           		//BufferedOutputStream(dest));

	         byte data[] = new byte[BUFFER];
	         // get a list of files from current directory
	         File f = new File("C:\\Users\\Zz85\\Desktop\\DictionaryProject\\Dictionary\\.");
	         String files[] = f.list();

	         for (int i=0; i < files .length; i++) {
	            System.out.println("Adding: "+f.getParent() + File.separatorChar +files[i]);
	            FileInputStream fi = new
	              FileInputStream(f.getParent() + File.separatorChar +  files[i]);
	            origin = new
	              BufferedInputStream(fi, BUFFER);

	            File toTar = new File (f.getParent() + File.separatorChar +files[i]);
	            TarEntry entry = new TarEntry(toTar);
	            entry.setName(toTar.getName());
	            //TarEntry entry = new TarEntry(files[i]);
	            //entry.setSize( toTar.length());
	            //entry.setModTime(toTar.lastModified());

				out.putNextEntry(entry);
	            /*
	            while (true) {
	            	//System.out.println("Bad");
					int count = origin.read(data, 0, data.length);
					if (count <= 0)
						break;
					out.write(data, 0, count);
				}*/
	            /**/
	            int count;
	            while((count = origin.read(data, 0,
	              BUFFER)) != -1) {
	               out.write(data, 0, count);
	            }
	            out.closeEntry();
	            origin.close();
	         }
	         out.close();
	      } catch(Exception e) {
	         e.printStackTrace();
	      }
	   }

}

Notice the how the lines BufferedOutputStream(dest)); can be swaped with BufferedOutputStream(new GZIPOutputStream(dest))); to BufferedOutputStream(new ZOutputStream(dest,JZlib.Z_BEST_COMPRESSION))); to give an different compression easily using its wrapper classes.

Next will the issue on how to decompressing them.

My First NDS HomeBrew: Rubik Cube Timer

Dedicated to my friend Lionel, whom made me revisit my interest in playing the Rubik’s Cube Puzzle.

rubik timer 1.0 screenshot

A Rubik’s Cube Timer, it is created to time time taken to solve the cube (Mine timings are usually between 1 and 3mins so no hours, or milliseconds implemented yet). The idea came after watching speed cubing videos online, we saw they had a special timer which they bang on to mark their completion.

Written in PaLib, here’s the code.
Visit this thread at PALib’s forums to download the files too.

/*

Zz85 Rubik Cube's Timer
App for Speed Cubing, for timing completion of puzzle.

RELEASES
Version 1.0 May 1, 2007 - Labour Day's Treat for my doctor-to-be friend Lionel

PLANS
Use hardware clock
Use nice sprints
Use sounds

*/

// Includes
#include <pa9 .h>       // Include for PA_Lib

	u16 RESET = 0;
	u16 START = 1;
	u16 END = 2;

	u16 status = RESET;

void reset()
{
	PA_OutputText(1, 6, 6, "%c1Ready...");
	PA_OutputText(1, 6, 8, "       ");
	PA_OutputText(1, 6, 12, "    ");
	status = RESET;
}

void start()
{
	PA_OutputText(1, 6, 6, "        ");
	PA_OutputText(1, 6, 8, "%c5Start!");
	status = START;
}

void end()
{
	PA_OutputText(1, 6, 12, "%c5End!");
	status = END;
}

int main()
{
	PA_Init();    // Initializes PA_Lib
	PA_InitVBL(); // Initializes a standard VBL

	PA_InitText(1, 2);
	PA_OutputText(1, 4, 2, "%c4Zz85's %c1Rubik %c2Cube %c3Timer!");

	PA_OutputText(1, 0, 16, "%c2Instructions:");
	PA_OutputText(1, 0, 18, "%c2Press Start for reset. Any keys or touchpad to start and stop.");
	PA_OutputText(1, 0, 21, "%c2Happy Cubing!");

	u32 ticks = 0;
	// Infinite loop to keep the program running
	while (1)
	{
		if (status == END && Pad.Released.Start) reset();
		else if (status == RESET)
		{
			ticks = 0;
			if  (Pad.Released.Anykey || Stylus.Released)  start();
		}
		else if (status == START)
		{
			ticks++;
			PA_OutputText(1, 6, 10, "%c5Time: %c0%d mins %d s      ",(ticks/3600),(ticks/60 %60));
			if  (Pad.Newpress.Anykey || Stylus.Newpress) end();
		}

		PA_WaitForVBL(); // Wait for 1/60 of a second
	}

	return 0;
}

More news & forums coverage at dcemu and neoflash