Archive for Cool Stuff

Pyipopt, Python marries with Ipopt

Ipopt is a leading nonlinear optimization tool. There are a bunch of interfaces, e.g. C/C++ standard interfaces, Java and MATLAB interface, FORTRAN interface for programmers.  However, no existing interface to python was presented. I started to connect ipopt with python two months ago inspired by OpenOpt. After lots of extensive development and nasty testing,  today, I proudly announce that the python interface of ipopt, aka, pyipopt, version alpha, is ready to go.

With the help of this module, in python, you can just use

import pyipopt
nlp = pyipopt.create(n, xl, xu, m, gl, gu, nnzj, nnzh, f, gradf, g, gradg, h, apply_new)
solution = nlp.solve(x0)

to get your NLP problem which n variables (xl, xu are boundaries for variables), m constraints (gl, gu are boundaries for constraints), and objective function f (gradf is the gradient, h is the Hessian matrix) with constraints g (gradg is the Jacobian value) optimized by IPOPT.

The package is available via google code: http://code.google.com/p/pyipopt/   An OpenOpt hooker is under development.

The code has BSD license. you can use this module whatever you want. For bug report and other related things, reach me at youxu AT wustl.edu.

To write a  package is not rocket science, but it might save you some time in your research.

[Special thanks to Dmitrey Kroshko from OpenOpt and Scipy community; Dominique Orban from Nlpy community]

Comments (1)

大型MMORPG杀人游戏”际莎”开始内测

经过长期深入研究魔兽世界和传奇等游戏, 我公司一名实习生, 联合世界上最大的网络服务提供商 Google, 作为 Google Summer Code 的一个项目, 利用 100% 的业余时间, 开发出了一款基于Gtalk 的大型多人在线角色扮演游戏: Gtalk 版杀人游戏际莎 (下文简称为际莎). 本游戏具有如下特点:

1. 三大职业系统: 警警察察, 平民和杀手. 三小职业系统: 城管: 看上去像警察其实是杀手的. Leon: 看上去是杀手其实不太冷的平民. 便衣: 看上去是平民其实是警察的. 各个职业都具有转生系统, 玩家可以自由选择偏好.

2. 无经济和武侠系统. 在巨人等网游充分利用猪肉涨价赚取用户道具钱的时候, 本游戏不使用任何道具,一举解决长期困扰韩国网游的玩家打道具赚钱的弊端. 无武侠系统使得白领玩家和学生一族不会练功走火入魔,促进社会和谐.

3. 公会即时通信支持. 本机器人可实现一定程度的语音识别, 自动将用户声音识别并以文字传送给特定玩家,使得您海内存知己, 晤言一室中. 真正意义上实现了杀人游戏的乐趣. 同时用户还可以通过及时免费的文字通信掌握游戏动态. 短信不收取信息费.**

4. 低配置的客户端支持. 根据我们测试结果, 奔腾 66Mhz 计算机可以顺利运行我们的游戏客户端. 在游戏客户端越来越大, 对显卡要求越来越高的今天, 我们反其道行之, 使用简单的网络协议, 让您在浏览器中即可实现游戏. 强大的协议使得您可以选择苹果或者Linux等小众平台, 同时老板键可以让你一键切换到 word/excel. 您还可以在 excel 里面边做表格边操作游戏. 目前支持的系统有 Windows 3.2, DOS 6.22, Linux 0.01+, 苹果 OS 8+, SUN OS3+ 和 MINIX. 硬盘 10Mb+, 处理器 1MHz +, 显卡不是必须配置.

5. 防沉迷系统. 家长不必担心孩子沉迷游戏, 因为按照我们和Google签订的协议, 未满18岁不能获得游戏所需Google 账号*. 成年人在连续6小时后, 自动转入休息模式. 系统自动播放轻柔的背景音乐让您获得充分休息+.

6. 强大服务器和网络支持. 目前该系统运行于三台 SUN Ultra II 和 4 台AMD 64 组成的集群上, 光纤接入美国信息高速公路骨干网. 电信网通均可接入, 延时不超过0.01ms, 可支持5000人同时在线. ultra-enterprise2.jpg

际莎内测期间,小规模放号, 请加 sharenyouxi@gmail.com 为好友.^ 一旦内测稳定, 即转入公测, 不删号, 经验值和等级可积累. 本游戏承诺永远免费**.

附注:

* 其他服务商可能不限制jabber 账号注册年龄, 由此带来的一切负担本公司概不承担.

+ 本功能可能需要高速网络连接支持, 如 ADSL.

** Google 可能会在杀人游戏过程中加入广告, 用户必须接受此才能游戏.

^ 先别加了, 各位愚人节快乐. 这个机器人短期肯定会上线. 到时候欢迎内测, 永远免费.

Comments (6)

几个趁手语句

处于局域网中的小型开发团队常常需要互相贴代码, 传文件, 共享资源, 我长期使用过程中总结了几行趁手的语句, 贴出来共享. (本文不适合 windows 用户)

1. Gtalk 传递命令行程序输出信息

常常需要把程序的输出结果或者调试结果通过 IM 发给同事诊断. 而这些结果通常都在字符界面下,拷贝出来很麻烦,于是,我写了一个小程序 gpipe.py,可以把 gtalk 当作一个管道接在程序后面, 比如说, 想把程序编译结果给郝培强(tinyfool),

make 2>&1 | gpipe tinyfool

他的gtalk 客户端就被我用输出给淹没了.
有兴趣的还可以套接 gtalk, 把信息用 base64 编码, 接受方再解码, 如此一来, gtalk 就和Linux 中的管道一样, 将一个机器上的程序的输出套接到另一个机器上另一个程序的输入. 实践证明, 在跨平台的环境下这种做法比使用中间文件分别执行高效很多. 调试时间也大大减少.

2. 传送文件作为邮件附件.

使用matt 客户端,一行即可完成:
echo “Content” | mutt -s “Subject” -a file email@address.demo

这个方法对及时传输一些小文件非常有效, 特别是传送源代码. 还能起到存档备份的效果, 反正Gmail 那么大不用也浪费. 懒人还可以进一步用一个脚本包装, 比如我机器上就包装出了一个 sendboss.sh, 里面是:
echo “Hi, These are the file(s), thanks. Eric” | mutt -s “File” -a $* myboss_email@wustl.edu

这样我每次就只要 “sendboss.sh files” 就可以了. 我老板常常惊讶于我发送文件的反应速度.

3. 一行语句的HTTP文件服务器.

python -m SimpleHTTPServer

即可将当前目录开设为一个8000端口的http 服务器的根目录. 在局域网中,如果需要临时共享当前目录下的一个较大文件,这个方法简便安全,实在是居家旅行必备.

还有, 下载的时候使用 “wget -c” 可以断点续传,很多哥们好像不知道这个小花招.

4. NFS 共享文件夹

SVN 和 CVS 对于代码和文档控制得很好,可是团队中免不了有些 PDF 文档或者色戒电影需要全团队共享,又不需要送到版本控制系统里面。一个共享的文件夹很有必要. 最简单的方法是使用 NFS, 能够跨平台且性能稳定. 具体服务器设置可以参考这里,客户端只要

mount nfs_server:/dir /mnt/share

即可顺利使用此文件夹. 此法对于有电驴 bt 爱好者存在的团队来说,实在是必备良方.

Comments (8)

请懂量子力学的一起帮我参详一篇论文

文章名:

Ultimate Physical Limits to Computation [计算的终极物理极限]

作者: MIT 的 Seth Lloyd,  量子计算领域顶尖科学家.

概要:  计算机是一种物理系统,因此肯定服从物理系统的规律。文章研究了一千克的计算机最多一秒能执行多少次逻辑运算,最大存储容量是多少,并且给出了定量的结果。所以, 摩尔定律不能永续。

这些问题和我以前提到的比特每焦耳问题是很相似,但是我物理基础有限,不能全部理解。
本文发在 2000 年 Nature.地址: 

http://puhep1.princeton.edu/~mcdonald/examples/QM/lloyd_nature_406_1047_00.pdf

有兴趣的直接给我发邮件或者gtalk: xu.mathena [A@T] gmail.com

Comments (3)

How to give a program fake system time so that you can use it forever (Linux)

[Disclaim: It’s evil, don’t use it unless you are fighting with some even more evil software.]

Short Intro. [Skip it if you don’t know much about OS or aren’t interested in the technical detail ]

As you might know, every program on Linux system runs on the kernel instead of directly contacting with actual machine. For modern operation systems like Linux, BSD(Mac) and Windows, a mechanism called system call is used to request the system resources via operation system so that operation system has the full control of all programs. In brief, when user program need call a function in library, e.g. print in stdlib, library function forwards (usually library function is a light-weighed wrap of the system call) the request to operation system. Since the system is highly hierarchical and user program is built on the top of libraries and OS kernel, it’s possible to insert some layers in between program and OS to intercept the request. Don’t panic about the nerdy name. Actually this strategy is commonly used on Window platform in anti-virus software as well, because anti-virus software want to monitor every system resource usage for any program and prevent the malicious resource requests.

Here, we simply want to intercept a system call named “TIME” so that every time a program request the current time (so that it can verify whether the licence has expired), we feed the program with a fixed (fake) time. By fooling the program around, you can literally use a program forever. God, doesn’t this mean I can use all software forever? The bad news is for some OSs like Windows, it’s very hard to do system call interception as all the APIs are undocumented and software might have other ways to prevent this. The good news is lots of software on Linux and Mac are simply reading system time. Actually, only top developers and Microsoft partners know how to do system interception. However, for Linux, since the system itself is open source from bottom up, there is no way to prevent such kind of interception (Now you know why some software companies don’t like Linux :).

Approach 

On Linux, tons of methods are around. Here I just introduce three of them briefly under the assumption that you don’t have the source code of that software. [Otherwise you can just modify the source code]

Method 1: Intercept library call in linking time.

Sometimes you have a library (A) that can be used as a part of your program and you want to intercept the library call of that library (A). The best way and the easiest way is to write a fake function and link it in the compile time. This method is totally harmless to your system and very neat. If you can do some modification in makefile, then this procedure is totally transparent to both developer and user.

Method 2: Intercept system call in the run time

If you’ve already got a execute program, then there is no way to intercept the system call in compiling time. To intercept the system call in the run time, there are two ways. The first approach is putting the target program in a designed container. Typically, a container fork/create/call the target program as child process. Since in OS, parent process has accessibility to the child process, it can intercept syscalls easily via ptrace toolset. The second method is to hack the kernel, namely, to tell the Linux kernel to response syscall in a certain way. Since now Linux supports kernel module, a very convenience approach is to compile a program as kernel module and install it on the fly. However, this method is less flexible then the previous method as now all the syscall are intercepted, even for system calls from other programs. [Sure, you can restrict the module only applicable to a certain process via a pid comparison, but then you need to feed the kernel module with PID, it’s awkward ]

In my implementation, I use ptrace/container method. I’ve tried kernel module method but failed as there were not so much well-formed documents on Linux 2.6 kernel.

Here is my code, it’s self-explanatory, have fun with hacking. [Download the C file]

/* Faketime wraps a user program and feed it with user-specified fake system time
   so that it can be used forever without any “licence expired” problem
	 
    Copyright (C) 2007 Eric You XU, Washington University ( youxu [@T] wustl.edu ) 
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.
    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    GNU General Public License for more details.
    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 

*/

#include <sys/ptrace.h>
#include <asm/ptrace.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#include <stdio.h>
#include <sys/syscall.h>
#include <linux/user.h>

/*
Register layout defined linux/user.h, but actually in 
 asm-$(arch)/user.h
struct user_regs_struct {
        long ebx, ecx, edx, esi, edi, ebp, eax;
        unsigned short ds, __ds, es, __es;
        unsigned short fs, __fs, gs, __gs;
        long orig_eax, eip;
        unsigned short cs, __cs;
        long eflags, esp;
        unsigned short ss, __ss;
};
*/

/* Note that EAX now is RAX in x86-64
 	we can also find the actural offset for any register
 	from <asm-$(arch)/ptrace-abi.h>
#define RAX 24
*/

#define ORIG_RAX 44
/* ORIG_RAX stores the number of syscall */

#define SYS_TIME 13
/* Machine specific syscall number is defined in 
	unistd.h */

#define back_to_future 1175737392

/* Time is stored as a long interger in C, you can get 
	current time via time(NULL). Thus, it’s very easy to 
	get a long integer denoting some time in the past. 
	
	Python/Java can also be helpful in figuring this out 
	
	If you don’t know how, just keep in mind that 
	Dec. 1, 2007 is about 1196476452. 
	One day interval = 60*60*24 = 86400 [Time flies fast]
*/

char* host_program = “your program name here”;
char* arglist = “your program fake list here”;
/* Make modifications for these two lines, then 
	compile it via
		gcc faketime.c -o faketime
	use it via 
		./faketime
*/

int main()
{   pid_t child;
    long orig_rax, eax;

	 struct user_regs_struct regs;
	 int status;
    int insyscall = 0;
    child = fork();
    if(child == 0) {
        ptrace(PTRACE_TRACEME, 0, NULL, NULL);
        execl(host_program, arglist, NULL);
          }
    else {
       while(1) {
          wait(&status);
          if(WIFEXITED(status))
              break;
          orig_rax = ptrace(PTRACE_PEEKUSER,
                     child, ORIG_RAX, NULL);

          if(orig_rax == SYS_TIME ) { /* Intercept SYS_TIME syscall */
             if(insyscall == 0) { /* Syscall entry */
                insyscall = 1;
             			  }
         	 else { /* Syscall exit */
					ptrace(PTRACE_GETREGS, child, 0, &regs);
				   	/* We can also use ptrace(PTRACE_SETREGS, child ,RAX, &back_to_future); 
						but it doesn’t work. There might be some tricky here */
					regs.eax = back_to_future;
					ptrace(PTRACE_SETREGS, child, 0, &regs);
            	                 }
          } // End if with SYS_TIME 
       ptrace(PTRACE_SYSCALL, child, NULL, NULL);
        }
    }
    return 0;
}

Comments (4)

My plan about the “Read The F Manual” Project

A little bit history

Being in the academical area for years, one of my dreaming tool is an online collaborative paper reader . You can say it’s YouTube with documents, or Digg with pdf files–name actually doesn’t matter. The ultimate goal for this system is to support collaborative document reading/organization for professors and Ph.D. students. Since we now have Ajax (more interactive than before) and Flash(as powerful as PDF), I would expect an light-wighted solution. arXiv and Citeseer do really good jobs in storing and linking all the documents, but the ultimate goal for me is to read.

On winter 2006, I expanded my ambition to a larger project: read the f source code and read the f books (Here of course the f word means fine :). I launched my domain name rtfsc.org [now redirected to Apache.org]. Our team members thought that rtfsc was easier than rtfm because we only need to deal with text information instead of PDF file. However, we set ourselves on the wrong track. It turned out that if we let the users upload and update their codes all the time, we have to implement a Subversion or even a Sourceforge. For us, an online code-reading community without code management and code search is terrible, but we don’t have that much time to finish all these ambitions. The other obstacle comes from my lacking experiences of Ajax development. Anyway, at last, we gave up. We stopped the development after Christmas. On that week, I was the person of the year 2006.

New motivation

I have been thinking about this project for nearly one year without any action. Lots of similar projects were there during this year, for example, flashpaper, edocr and scribd. But none of these are my dreaming tool. I took a retrospect about our project again and found that nobody actually wanted to do that except us because they didn’t actually understand our requirements. Their goals are usually becoming the next DocTube thing, while my goal is to have a handy system open for academical research. Also, I found some open source tools that were really inspiring. These make me interested in the project again.

Technical aspects:

1. PDF to SWF is not so that hard, there is an open source tool: PDF2SWF.

2. I thought that I can’t control the converted SWF as there is no API exposed as Flashpaper, but I was wrong. Actionscript can control it directly. What I need to do is to learn Actionscript, which is not so that hard.

3. I was thought that Flashpaper use some undocumented APIs which we could never know, but I got SWFmill today and now I can study the code of Flashpaper. [Disclaimer: I didn’t say anything about how to decompile flashpaper or violate the EULA of flashpaper]

4. I thought Ajax + Flash development was hard and had a very steep learning curve, but again I was wrong. On hacking Google Finance these days, I found the Flash Ajax Integration Package, which is very handy to use for some newbie like me without any Ajax/Flash developing experiences.

Proof of concept

Here is a proof of concept product. I convert my PDF version CV to swf and then combined it to a controller I wrote based on the default controller provided in PDF2SWF. (This CV has two pages, you can proceed to next page by click the red arrow)

cv.swf

Final Word

What I need is an sophisticated viewer which can be as powerful as flashpaper can communicate with other Ajax components on that webpage. So for developers, if you find this idea interesting and you are good at Ajax/Flash, feel free to take this idea and do it, as I might not have time to do it or it will take me a long time to finish it. I desperately need an Ajax style flash-based document reader with inline comment support. If you can do thing and get your own startup based on the idea, my only request is letting me be your user.

BTW, if there was some lessons in this project, I would say, choose the handy tools before you get start.

Comments (1)

识别文本用哪种语言写成

ASPN Python Cookbook 提到了一个使用 zlib 库识别文本用哪种语言写成的程序. 其核心代码不超过20行, 据我观察, 识别精度不低于95%. 我略做了一下修改, 把联合国联合国人权宣言作为语料库,目前从 wikipedia 上随便抓一篇爪哇文的文章下来, 都能识别得九不离十。

class Entropy:
    def __init__(self):
		self.entro = []

    def register(self, name, corpus):
        “”"
        register a text as corpus for a language or author.
        <name> may also be a function or whatever you need
        to handle the result.
        “”"
        corpus = str(corpus)
        ziplen = len(zlib.compress(corpus))
        print name, ziplen
	self.entro.append((name, corpus, ziplen))

    def guess(self, part):
        “”"
        <part> is a text that will be compared with the registered
        corpora and the function will return what you defined as
        <name> in the registration process.
        “”"
        what = None
        diff = 0
        part = str(part)

        for name, corpus, ziplen in self.entro:
		nz = len(zlib.compress(corpus+part)) - ziplen
		if diff==0 or nz<diff:
                	what = name
        		diff = nz
        return what

先贴代码, 有时间细讲一下语言模型和信息论的妙用. 简单而小巧的模型解决看上去不可解决的问题, 这就是人工智能的精华.

[所有文件打包下载(包含语料源文件10Mb). 代码本身其实只有50行]

Comments (1)

A simple grabber to get unlimitted number of items from RSS

Recently I have to get some historical data from one RSS feed. It seems that RSS can only output a limited number of recent items. Since in Google Reader, we can always roll to previous item [if there is one], my solution here is to use Google Reader as the feed processor.

Actually I am not the first one to do this. gPowered and  GoogleReaderAPI have already made it possible. I extract the necessary code here and omit other lines. As usual, it’s Python.[download]

“”" wuFetcher
	Usage: python wufetcher.py

	Author: Eric You XU, Washington University
	[Free to use for whatever purpose, absolutely NO WARRANTY]
	Kudos to 	gPowered: 			http://blog.gpowered.net/2007/08/google-reader-api-functions.html
				GoogleReaderAPI		http://code.google.com/p/pyrfeed/wiki/GoogleReaderAPI
“”"

import urllib
import urllib2
import re  

login = ‘wufetcher@gmail.com’
password = ‘wuFetcher2007′
source = ‘wuFetcher’

google_url = ‘http://www.google.com’
reader_url = google_url + ‘/reader’
login_url = ‘https://www.google.com/accounts/ClientLogin’
get_feed_url = reader_url + ‘/atom/feed/’

def get_SID():
	header = {‘User-agent’ : source}
	post_data = urllib.urlencode({ ‘Email’: login, \
								‘Passwd’: password, \
								’service’: ‘reader’, \
								’source’: source, \
								‘continue’: google_url, })
	# @see GoogleReaderAPI: Identification

	request = urllib2.Request(login_url, post_data, header)
	try :
		f = urllib2.urlopen(request)
		result = f.read()
		print result
	except:
		print ‘Error logging in’
		exit(-1)
	return re.search(‘SID=(\S*)’, result).group(1)

def get_results(SID, url, number):
	header = {‘User-agent’ : source}
	header[‘Cookie’]=‘Name=SID;SID=%s;Domain=.google.com;Path=/;Expires=160000000000′ % SID
	post_data = urllib.urlencode({‘n’: str(number)})
	request = urllib2.Request(url+‘?n=’+str(number), None, header)
	try :
		f = urllib2.urlopen( request )
		return f.read()
	except:
		print ‘Error getting data from %s’ % url
	return None

if __name__ == “__main__”:
	sid= get_SID()
	feed_url= “http://feeds.feedburner.com/xumathena”
	# replace this url with the rss feed you want to fetch

	number = 10
	# replace this number with number of items you want to fetch

	result = get_results(sid, get_feed_url+feed_url.encode(‘utf-8′), number)
	f = open(feed_url.split(‘/’)[-1], ‘w’)
	f.write(result)
	f.close() 

Comments

Build VHDL simulation tool chain on Linux

I take Computer Architecture course this semester and study basic VHDL for digital design. The instructor recommends ModelSim with both Windows and Linux versions. But unfortunately, ModelSim for Linux can only be installed on RH Linux. I tried to install it on Ubuntu but obviously it didn’t work. It turned out that the only solution would be using ModelSim for Windows in our computer lab. But as a dead-head Linux fan, I simply want to find alternative software to get things done on Linux platform. After some googling and asking help from friends, I found two handy software packages that form a tool chain to do VHDL simulation on Linux: GHDL and GTKWave.

What

GHDL is an amazing package that it employ gcc and compile VHDL code to objective code. It can’t translate your design into a netlist but it’s sufficient for us to do the simulation.
GTKwave is another tool which can help you view the wave form dumped by GHDL simulation. There two, in principle, can help you handle all the VHDL simulation tasks involved in a one-semester-course like computer architecture.

How

Build the tool chain

If you are using a Debian family (Debian/Ubuntu, etc) Linux, an apt-get will save your life. Try:
apt-get install ghdl
and
apt-get install gtkwave.
[You might need sudo or run it as root.]

If you not, try to download the package and read the README. It’s easy. If you want to install it on Mac as what I’ve done, remember to install X11. The whole procedure should take you less than five minutes.

How to use it

It’s very simple. GHDL will compile the VHDL code for you to object code and convert it to executable. For example, if I have CPU.vhdl which is a simple computer description. Try to type:

ghdl -a cpu.vhdl

to compile it, and

ghdl -e cpu

to make executable file (do linking).

Finally you can use

./cpu --help

to see how to run it.

Some tips:
If you include ieee package, add this option: –ieee=synopsys
If you want to let the simulation run certain amount of time, use something like

./cpu --stop-time=100ns

If you want to dump a signal wave format for gtkwave, just add –vcd=vcd.file

After that, you can use

gtkwave vcd.file to see the wave. You might need to add all the signals to the wave window via “Search->Signal Search Tree”.

Why

You might ask why it’s handy than ModelSim. It’s obvious. For example, if you write a shell script that can issue all the compiling/dumping/viewing command in the right order, you only need two keyboard stoke to run a test, in comparing with in ModelSim, where you need to do at least 10 mouse click and maybe type these commands:

view wave
add wave -r /*
"set format, etc"

Finally, you can use GHDL as your VHDL code formatter and get a very nice HTML format for your neat code. You can now make it even neater, why not :)

Some really missing features for these small tools.

1. Non-standard signal watch.

If you have a signal which is an array, it’s not handy to view the wave as ghdl doesn’t actually output the signal changing information for this signal.

2. Automatic dependency solving.

Currently GHDL will complain about the dependency, but it doesn’t actually handle this like GNU make. Therefore, you have to either write your own makefile to use make to manage your code dependency, or recompile all the code every time.

My example code of a silly CPU:

    1 – CSE 560 Homework, a simple CPU
    2 – Eric You XU
    3 — version 0.05
    4
    5 library ieee;
    6 use ieee.std_logic_arith.all;
    7 use ieee.std_logic_signed.all;
    8 use ieee.std_logic_1164.all;
    9
   10 entity CPU is
   11         port (  IR      :       in std_logic_vector (31 downto 0);
   12                 READY   :       in bit;
   13                 CLK     :       in bit
   14                 );
   15 end entity CPU;
   16
   17 architecture behav of CPU is
   18     type reg_type is array(0 to 255) of std_logic_vector(31 downto 0);
   19     signal storage: reg_type;
   20
   21     signal d1, d2: std_logic_vector(31 downto 0);
   22     signal raw1, raw2: std_logic_vector(31 downto 0);
   23     signal s1_int, s2_int: integer;
   24     signal prod: std_logic_vector(63 downto 0);
   25     signal status:      std_logic_vector(1 downto 0);
   26     signal phase:       bit;
   27     signal index:       integer;
   28     signal opcode:      std_logic_vector(2 downto 0);
   29     signal needd2:      bit;
   30
   31 begin
   32
   33
   34
   35 process(clk)
   36    begin
   37     if (ready=‘0′) then
   38         phase <= ‘0′;
   39 – For test
40 storage(0) <= X”00000004″;
   41 storage(1) <= X”FFFFFFFD”;
   42 storage(2) <= X”01010103″;
   43 storage(3) <= X”0F0F0F08″;
   44 storage(4) <= X”F0F0F0F0″;
   45 storage(5) <= X”FFFFFFFF”;
   46 storage(6) <= X”00000000″;
   47 storage(7) <= X”0000000E”;
   48 storage(8) <= X”00000004″;
   49 storage(9) <= X”DEADBEEF”;
   50
   51      else
   52        if(clk’event) then
   53           if(clk = ‘1′) then                    – CLK _| 
   54               if(phase = ‘0′) then              – state 1, read instructions
   55
   56                   opcode        <=      IR(26 downto 24);
   57                   – 31 30 29 28 27 26 25 24: Lower 3 bit
   58                   raw1 <= storage(ieee.std_logic_unsigned.conv_integer( IR(23 downto 16) ));
   59                   raw2 <= storage(ieee.std_logic_unsigned.conv_integer( IR(15 downto 8) ));
   60                   – RAW Hazard 
   61                   –avoid to use s1_int = con_int(raw1)
   62                   s1_int        <=      ieee.std_logic_signed.conv_integer(storage(ieee.std_logic_unsigned.conv_integer( IR(23 downto 16) )));
   63                   s2_int        <=      ieee.std_logic_signed.conv_integer(storage(ieee.std_logic_unsigned.conv_integer( IR(15 downto 8) )));
   64                   index <= ieee.std_logic_unsigned.conv_integer(IR(7 downto 0));
   65
   66               else                              – state 3, write register files
   67                 case opcode is
   68                         when “000″ => – ADD
   69                                 storage(index) <= d1;
   70                         when “001″ => – SUB
   71                                 storage(index) <= d1;
   72                         when “011″ =>
   73                                 storage(index) <= d1;
   74                         when “100″ => – INC
   75                                 storage(index) <= d1;
   76                         when “101″ => – DEC	
   77                                 storage(index) <= d1;
   78                         when “010″ => – MULT
   79                                 storage(index) <= prod(31 downto 0);
   80                                 d2 <= prod(63 downto 32);
   81                                 d1 <= prod(31 downto 0);
   82                                 if (index = 255) then
   83                                          storage(0) <= prod(63 downto 32);
   84                                 else
   85                                          storage(index+1) <= prod(63 downto 32);
   86                                 end if;
   87                         when “110″ => – DIV
   88                                 storage(index) <= d1;
   89                                 if (index = 255) then
   90                                          storage(0) <= d2;
   91                                 else
   92                                          storage(index+1) <= d2;
   93                                 end if;
   94                         when others =>
   95                                 report “Invalid OpCode.” severity FAILURE;
   96                   end case;
   97              end if;
   98
   99            else                                 – CLK |_		
  100               if(phase = ‘0′) then              – state 2, ALU step
  101
  102                   case opcode is
  103                      when “000″ =>  – ADD
  104                                 d1 <= conv_std_logic_vector((s1_int + s2_int), 32);
  105                                 needd2 <= ‘0′;
  106                      when “001″ => – SUB
  107                                 d1 <= conv_std_logic_vector((s1_int - s2_int), 32);
  108                                 needd2 <= ‘0′;
  109                      when “011″ => – COMP
  110                                 d1 <= conv_std_logic_vector((-s1_int - 1), 32);
  111                                 needd2 <= ‘0′;
  112                      when “100″ => – INC
  113                                 d1 <=  conv_std_logic_vector((s1_int + 1), 32);
  114                                 needd2 <= ‘0′;
  115                      when “101″ => – DEC
  116                                 d1 <=  conv_std_logic_vector((s1_int - 1), 32);
  117                                 needd2 <= ‘0′;
  118                      when “010″ => – MULT
  119                                 – If I assign the prod value to d1 and d2 here, a RAW hazard will occur.			
  120                                 prod <= raw1 * raw2;
  121                                 needd2 <= ‘1′;
  122                      when “110″ => – DIV
  123                                 d1 <= conv_std_logic_vector((s1_int/s2_int), 32);
  124                                 d2 <= conv_std_logic_vector((s1_int rem s2_int), 32);
  125                                 needd2 <= ‘1′;
  126                      when others =>
  127                              report “Invalid OpCode.” severity FAILURE;
  128                   end case;
  129
  130
  131                   phase <= ‘1′;
  132                else                             – state 4: NOP, Increase PC, etc.
  133
  134                   – Set STATUS —
  135                   status <= “00″;
  136                   if(needd2 = ‘0′) then – only look at d1
  137                       if d1 = X”00000000″ then
  138                           status <= “01″;
  139                       end if;
  140                       if d1(31) = ‘1′ then
  141                           status <= “10″;
  142                       end if;
  143                       if d1 = X”FFFFFFFF” then
  144                           status <= “11″;
  145                       end if;
  146                   else – needd2 = 1
  147                      if d1 = X”00000000″ and d2 = X”00000000″ then
  148                          status <= “01″;
  149                      end if;
  150                      if d2(31) = ‘1′ and opcode = “010″ then            – high order bit of mult is 1
  151                         status <= “10″;
  152                      else
  153                         if d1(31) = ‘1′ and opcode = “110″ then         – high order bit of div is 1
  154                            status <= “10″;
  155                         end if;
  156                      end if;
  157                      if d1 = X”FFFFFFFF” and d2 = X”FFFFFFFF” then
  158                          status <= “11″;
  159                      end if;
  160                   end if;
  161                   ——————
  162
  163                   phase <= ‘0′;
  164               end if;
  165           end if;
  166        end if;
  167     end if;
  168
  169 end process;
  170 end architecture behav;

Comments (1)

给那些说Linux图形界面不好看的人

iTunes 型窗口切换
Shift Window

Tab 切换窗口时小图动态变化
Tab Switch

平铺桌面
screenshot-2.png

桌面也是展台, 记得配上美女图
Reflect

苹果上的 Expose 效果
screenshot-4.png

我现在就在这么绚的环境下工作 :)

(装一个 Ubuntu 你就可以拥有这一切, 为何还在买世界找盗版的Vista.)

Comments (8)

« Previous entries