Friday, October 11, 2013

AES (Advanced Encryption Standard)

I'm not gonna teach you how to perform AES encryption or decryption. So if you are looking for that, then you can turn right around and go. But I will tell you some interesting things that I learned about AES. These may help you in conjunction with other tutorials.

1. Multiply is not multiply. You will need a function to perform gmul. It is multiply in a Galois field. I don't really know much about what a Galois field is, but it is an alternate universe when it comes to mathematics. So when they say multiply, this is what they mean.

2. Add and subtract are actually XOR. Wherever it says subtract it is the same operation as add. Realize that every step of AES (key generation, adding round keys, substitute bytes, shifting rown, and mixing columns) require Galois operations. Multiply, add / subtract.

3. Decryption is harder than encryption. Yes, that sounds weird, but it's true. What I mean is that to perform encryption you just need the key to begin with. You can actually generate the keys on the fly. To perform decryption, you MUST perform full key expansion to get the final key. They you can work backwards on the fly. Also decryption's inverse mix columns step requires 4 multiply look-up tables as opposed to 2 for encryption's mix columns step.

4. AES 256 is easier to implement than AES 192. The biggest difficulty is on the fly key generation. If you want to generate AES 128 on the fly, then it is the same sequence for each round of encryption. For 256, it is the same round every 2 times. For 192, it is different. B/c each round of key expansion produces 192 bits (24 bytes) and each round of encryption uses 16 bytes, you have to loop through 1.5 rounds of encryption before starting a new line of key expansion. Of course AES 256 requires more flops.

Thursday, August 22, 2013

SystemVerilog array of objects initialization

So I'm updating one of my testbenches and I want to create an array of objects. For example:
A_class a_instance[num];

I also want to pass these objects to modules and other created objects.

B_class b_instance = new (a_instance[0]);
C_mod c_modinst (.a(a_instance[0]));

The biggest issue is that a_instance isn't yet initialized.

If you try and initialize with

initial begin
for(genvar i = 0; i < num; i++) a_instance[i] = new();

This won't work. Has something to do with object and module creation running before initial lines. The initial statement is too late, a null object was passed in and that's what the object and modules will have.

When I was passing a non array, it would work b/c the declaration included an assignment:
A_class a_instance = new();
but you can't call new on an array.

Here's what appears to work:
A_class a_instance = '{num{A_class::create()}};

This surprised me as I am using replication. It looks like each instance points to its own object. This resolves the problem. Now on the declaration line, I can initialize the objects. Passing the objects around works well now.

Update from Idan's comment:
A_class a_instance = '{default:A_class::create()};

This uses the default syntax for filling in an array. Much nicer than the replication mechanism.

About the create function: SystemVerilog doesn't allow you to call new on a class type so I use a create function instead:

class a;
 function new();
  $display("creating a");
 static function a create();
  class a_inst;
  a_inst = new();
  return a_inst;

I believe others refer to this as a factory create function or something like that. Now creating a is as easy as calling a::create().

Saturday, June 8, 2013

Installing rdesktop with user privileges (Red Hat EL 5.5)

Recently I came across a challenge of installing remote desktop without root privileges. Here is the information. Kudos to: for showing me how to do this.

In my home directory I performed these steps:
# make rpm database
mkdir rpmdb
rpmdb --initdb --dbpath ~/rpmdb/
# prepare folders
mkdir -p rpmtop/RPMS/i386
mkdir rpmtop/SRPMS
mkdir rpmtop/SOURCES
mkdir rpmtop/BUILD
mkdir rpmtop/SPECS
mkdir rpmtmp
echo `%_dbpath /home//rpmdb' | cat >> ~/.rpmmacros 
echo '%_topdir /home//rpmtop' | cat >> ~/.rpmmacros 
echo '%_tmppath /home//rpmtmp' | cat >> ~/.rpmmacros 
# copy system installed rpm list (must do this to meet dependency requirements of desired apps)
cp /var/lib/rpm/* rpmdb/.
# build rdesktop
rpmbuild --rebuild rdesktop-1.6.0-3.src.rpm
# install rdesktop
rpm -ivh rpmtop/RPMS/x86_64/rdesktop-1.6.0-3.x86_64.rpm
# since rdesktop uses keymaps by default from /usr/local, and since rdesktop isn't installed there, we will cheat by creating a link to 'user' available keymaps
ln -s usr/share/rdesktop/ ~/.rdesktop

This will give you:
which works wonderfully well for connecting to remote windows systems.

Saturday, May 18, 2013

Xilinx ISE (Project Navigator) x64 (64 bit) on Windows 8

Quick tip for those frustrated by file dialog crashes in Xilinx ISE x64 on Windows 8.

Rename libPortability.dll to libPortability.dll.orig, and copy libPortabilityNOSH.dll to libPortability.dll.
Do this in:
C:\Xilinx\14.5\ISE_DS\common\lib\nt64 (copy dll from first location)
This turns off SmartHeap.
This will fix ISE and iMPACT crashes on file dialogs.
This information was found from another thread, thank you howardp from Xilinx in this thread:

This doesn't resolve Vivado or PlanAhead issues. This only helps for ISE and iMPACT on Windows 8 x64.

Friday, January 4, 2013

SystemVerilog wish list and SV2012

So I've read up a bit on the newest SystemVerilog standard, SV 2012. There are a few simple things I like:
You can now call new from another object.
In SV 2009:
class cl_base;
class cl_ext extends cl_base;

So now I want to instantiate a cl_ext and point to it with a cl_base pointer.
Some people will code this verbosely:
cl_base cl_b_inst;
cl_ext cl_e_inst = new();
cl_b_inst = cl_e_inst;

I have always resolved this using another method in cl_ext:
static function cl_ext create();
cl_ext t;
t = new();
return t;

This way allows me to do this:
cl_base cl_b_inst = cl_ext::create();

But now, with SV 2012, you can directly call new:
cl_base cl_b_inst = cl_ext::new();

Now onto the next improvement that I am excited about: Multiple Inheritance! The new SV 2012 now supports multiple inheritance by using an interface class. Don't know how that works as I haven't used it yet.

Now, onto my wishlist:
Allow constant functions to call system tasks. For example:
localparam blah = $urandom();
That'd help for some of my randomized teesting

Variable length arguments would be nice, make it easier to create a new display function with added parameters.

Pass signals directly into a class, but of course... that will never happen. For now you just have to wrap signals in an interface to keep them handy for a class to use.

Allow multi dimensional arrays with both types and widths:
wire [count - :0] int my_integers;

Allow for seamless multidimensional array flipping:
wire [a_count - 1:0] [b_count - 1:0] wires_a_by_b;
for(int bi = 0; bi < b_count; b++)
  b_reduce[bi] = $flip(wires_a_by_b)[b];

or something like that... This might work with a function, but I do believe that SystemVerilog still doesn't support unconstrained types for a function.

Generate statements in a class:
SV supports parameters in a class, but it won't allow for generate statements in a class. This is both unexpected, and annoying. If parameters are allowed appear identical to parameters for a module or interface, then they should behave more or less the same!

Wildcard connections of parameters. It would've helped me today.

I know there is something I want having to do with clocking blocks... One second, I have to find it...
So I want some indication of when a clocking block updates a signal. See forum post for more information.

Here's the link to my question:

Now onto Cadence:
PLEASE allow modports inside generate statements!

I know there is more, but I can't recall now sitting in front of the TV.