2009/06/30

An English-to-Chinese Dictionary based on the evil Google Suggest Quries


<SearchPlugin xmlns="http://www.mozilla.org/2006/browser/search/">
<ShortName>gDictionary</ShortName>
<Description>Google English-Chinese Dictionary</Description>
<InputEncoding>UTF-8</InputEncoding>
<Image width="16" height="16">data:image/png;base64,AAABAAEAEBAAAAEAGABoAwAAFgAAACgAAAAQAAAAIAAAAAEAGAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADs9Pt8xetPtu9FsfFNtu%2BTzvb2%2B%2Fne4dFJeBw0egA%2FfAJAfAA8ewBBegAAAAD%2B%2FPtft98Mp%2BwWsfAVsvEbs%2FQeqvF8xO7%2F%2F%2F63yqkxdgM7gwE%2FggM%2BfQA%2BegBDeQDe7PIbotgQufcMufEPtfIPsvAbs%2FQvq%2Bfz%2Bf%2F%2B%2B%2FZKhR05hgBBhQI8hgBAgAI9ewD0%2B%2Fg3pswAtO8Cxf4Kw%2FsJvvYAqupKsNv%2B%2Fv7%2F%2FP5VkSU0iQA7jQA9hgBDgQU%2BfQH%2F%2Ff%2FQ6fM4sM4KsN8AteMCruIqqdbZ7PH8%2Fv%2Fg6Nc%2Fhg05kAA8jAM9iQI%2BhQA%2BgQDQu6b97uv%2F%2F%2F7V8Pqw3eiWz97q8%2Ff%2F%2F%2F%2F7%2FPptpkkqjQE4kwA7kAA5iwI8iAA8hQCOSSKdXjiyflbAkG7u2s%2F%2B%2F%2F39%2F%2F7r8utrqEYtjQE8lgA7kwA7kwA9jwA9igA9hACiWSekVRyeSgiYSBHx6N%2F%2B%2Fv7k7OFRmiYtlAA5lwI7lwI4lAA7kgI9jwE9iwI4iQCoVhWcTxCmb0K%2BooT8%2Fv%2F7%2F%2F%2FJ2r8fdwI1mwA3mQA3mgA8lAE8lAE4jwA9iwE%2BhwGfXifWvqz%2B%2Ff%2F58u%2Fev6Dt4tr%2B%2F%2F2ZuIUsggA7mgM6mAM3lgA5lgA6kQE%2FkwBChwHt4dv%2F%2F%2F728ei1bCi7VAC5XQ7kz7n%2F%2F%2F6bsZkgcB03lQA9lgM7kwA2iQktZToPK4r9%2F%2F%2F9%2F%2F%2FSqYK5UwDKZAS9WALIkFn%2B%2F%2F3%2F%2BP8oKccGGcIRJrERILYFEMwAAuEAAdX%2F%2Ff7%2F%2FP%2B%2BfDvGXQLIZgLEWgLOjlf7%2F%2F%2F%2F%2F%2F9QU90EAPQAAf8DAP0AAfMAAOUDAtr%2F%2F%2F%2F7%2B%2Fu2bCTIYwDPZgDBWQDSr4P%2F%2Fv%2F%2F%2FP5GRuABAPkAA%2FwBAfkDAPAAAesAAN%2F%2F%2B%2Fz%2F%2F%2F64g1C5VwDMYwK8Yg7y5tz8%2Fv%2FV1PYKDOcAAP0DAf4AAf0AAfYEAOwAAuAAAAD%2F%2FPvi28ymXyChTATRrIb8%2F%2F3v8fk6P8MAAdUCAvoAAP0CAP0AAfYAAO4AAACAAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAQAA</Image>
<Url type="application/x-suggestions+json" method="GET" template="http://suggestqueries.google.com/complete/search?client=suggest&amp;hjson=t&amp;ds=d&amp;hl=zh-CN&amp;q={searchTerms}"></Url>
<Url type="text/html" method="GET" template="http://www.google.com/dictionary?aq=f&amp;langpair=en|zh-CN&amp;hl=en&amp;q={searchTerms}"></Url>
<SearchForm>http://www.google.com/dictionary</SearchForm>
</SearchPlugin>

2009/06/29

Small Skills of Command Prompt for Windows

There are some useful skills for CMD.exe in Windows.

1, How to do a substring in the CMD.exe -- %VAR_NAME:~POS,LEN%
for example
set name=fingercat
echo %name:~6,3%
This will give you a "cat" ;)

2, How to get the input of user as a string?
On windows 2000 or later. It is simple.
set /p answer=Prompt Message Here
echo %answer%
This will give you the input stirng of user.

Windows Command Prompt (.bat) file never suppose to be a powerful shell. But Microsoft really give it more an more power until a real PowerShell came into place.

2009/06/10

Inside the Erlang VM - focus on SMP

It discussed the current status and possible future of SMP enabled Erlang VM.
It is worth to read!

2009/04/22

VIMRC file


source $VIMRUNTIME/vimrc_example.vim
source $VIMRUNTIME/gvimrc_example.vim
set nobackup
set ch=1
set tabstop=4
set shiftwidth=4
"set softtabstop=4
set expandtab
colorscheme darkblue
"colorscheme oceandeep


" Enable the Chinese characters
set guifont=Bitstream\ Vera\ Sans\ Mono:h10:cANSI,NSimSun:h12:cGB2312
set guifontwide=NSimSun:h12:cGB2312


" display the syntax name under the cursor
map <F12> :echo synIDattr(synIDtrans(synID(line("."), col("."), 1)), "name")<CR>


" We can navigate the list by using the <F3> and <S-F3>
map <F3> :cnext<CR>
map <S-F3> :cprevious<CR>


" Let's help the tab navigation a little
map <F9> :tabprevious<CR>
map <S-F9> :tabnext<CR>


" Tlist
map <F5> :Tlist<CR>
set tags=./tags,../tags,../../tags

2009/03/15

C++ reinterpret_cast

说起 C++ 的类型转换,一共有四种:

  • dynamic_cast
  • static_cast
  • reinterpret_cast
  • const_cast
其中 reinterpret_cast 是很有意思的,它可以被看作是 C 语言中强制类型转换的功能,它是一种非检查的暴力转换手段。通过它,我们可以把 指向 int* 转换为 double* 。

当然也可以用来做函数指针的转换,比如:

void FuncA(char *src, int len, int *pLen)
{
*pLen = len;
}

int _tmain(int argc, _TCHAR* argv[])
{
bool (*func_ptr) (char*, int);

func_ptr = reinterpret_cast<bool (*)(char*, int)>(&FuncA);

return 0;
}

当然了也可以用来转换 类成员函数,如:

class ObjectA
{
public:
void FuncA(char *src, int len, int *pLen)
{
*pLen = len;
}

bool FuncB(char *src, int len, int *pLen)
{
*pLen = len;
return false;
}
};

class ObjectB
{

};

int _tmain(int argc, _TCHAR* argv[])
{
bool (ObjectB::*func_ptr) (char*, int);

//ObjectA obj;
func_ptr = reinterpret_cast<bool (ObjectB::*)(char*, int)>(&ObjectA::FuncB);

return 0;
}

但是不能在普通函数和类成员函数之间转换。

2009/02/25

Install Safari4 without installation on Windows

First, Extract the Safari.cab into a folder. The Safari.cab is from Safari.msi of SafariSetup.exe, you can open the .exe and .msi by using 7-zip tool. :D

Second, put the file into the right folder. If you have MinGW or Cygwin, you can use this script to move all the files into the right folder.

for i in *; do fp=${i//_/\/}; echo $fp; f=$(basename $fp); eval "p=\${fp%$f}"; if [ $fp != $f ];then if [ ! -d $p ];then mkdir -p $p; fi; mv $i $fp; fi; done


Now ready to go! Safari4 beta is a green software.

2009/02/16

NORTEL 幽默

NORTEL 从来就不缺乏有才华的人,这个我曾经工作过的百年老店今天已经是风雨飘摇。
看看这些 NORTEL 员工们制作的讽刺剧吧!

我不得不赞叹,太油菜了!

2009/01/20

Java GUI Effectives

Java gets widely usage on Server side, while the client technology is still evolution continuously. Since Java 5.0, more and more interesting GUI feature are added into the JVM. They are:
  • OpenGL-based render pipeline
    As you know, Swing renders all the widgets by itself, that's the reason why some case the Java GUI looks so strange. :) Previously on Microsoft Windows, the DirectDraw and Direct3D was the only choice. But now you can use OpenGL pipeline as well.
    It is disabled by default, but it can enabled by setting
    -Dsun.java2d.opengl=true
  • Font Anti-Aliasing
    It is an important feature for the font anti-aliasing. Now it is possible for Java application to specify the Font Anti-Aliasing feature by itself with system property:
    -Dawt.useSystemAAFontSettings=lcd

  • Metal and Nimbus Look and Feel
    Metal (from Java 5.0) and Nimbus (from Java 6.0u10) are available in standard JRE distribution.
Really hope Java could be better and better~~~

2009/01/16

C++ vtable

在 C++ 的OO模型中,很重要的一个特性是运行时多态。运行时多态是通过类的虚方法实现的。看下面这个例子:


struct IObject {
  virtual void MethodA() = 0;  
  virtual int  MethodB(char *) = 0;
};

class A : public IObject {
public:
  virtual void MethodA() {
    std::cout << "method A" << std::endl;
  };

  virtual int MethodB(char *p) {
    std::cout << "method B " << p << std::endl;
    return 0;
  };

public:
  int MethodC(int c) {
    std::cout << "method C non-virtual" << std::endl;
    return ++c;
  }
private:
  int mem_;
};

int main(int argc, cahr *argv[])
{
  IObject *pObj = new A;

  pObj->MethodA();
  pObj->MethodB(NULL);

  // FIXME: This is a compile error!
  pObj->MethodC(1); // error

  delete A;

  return 0;
};

C++ 运行时多态, 在执行代码中,主要通过 vtable 实现。让我们用C来重新描述上面的例子。


// VTABLE of class IObject
struct I_IObject {
  void *pMethodA(void);
  int  *pMethodB(char *);
};

// Instance variant type of IObject
struct IObject {
  struct I_IObject *vtable_this;
};

// VTABLE of class A
struct A;
struct I_A {
  void *pDtor(A*)
};

// Instance object variant type of class A
struct A {
  struct I_IObject *vtable_IObject;
  struct I_A *vtable_this;

  int *pMethodC(int);
  int mem_;
};

void A_MethodA (void) {
  printf("method A\n");
}

int  A_MethodB (char *p) {
  printf("method B %s\n", p);
}

int  A_MethodC (int c) {
  printf("method C non-virtual\n");
  return ++c;
}

void A_dtor(struct A *_this) {
  free(_this);
}

struct A *A_ctor() {
  struct A *p = malloc(sizeof(struct A));

  // Non-virtual function will be assign the value directly.
  p.pMethodC = &A_MethodC;

  /////////////////////////////////////////////////
  // vtable initialization code
#ifdef A_MethodA
  p.vtable_IObject->pMethodA = &A_MethodA;
#else
  p.vtable_IObject->pMethodA = &IObject_MethodA; // Warning!
#endif

#ifdef A_MethodB
  p.vtable_IObject->pMethodB = &A_MethodB;
#else
  p.vtable_IObject->pMethodB = &IObject_MethodB; // Warning!
#endif

  // vtable of A itself
  p.vtable_self->pDtor = &A_dtor;

  return p;
}

int main(int argc, char *argv[])
{
  IObject *pObj = (IObject*) A_ctor();

  pObj->vtable_self->pMethodA();
  pObj->vtable_self->pMethodB(NULL);

  A_dtor(pObj);

  return 0;
}




C的定价物确实有些繁琐,不过基本的结构就是这样了。具体说来是这样:
1,如果一个类 virtual function, 这些 virtual funciton 就会被统一在一个 vtable 中;
2,包含 virtual function 的class 都会有一个指向 vtable structure的指针,如果当前类重写了 virtual function, 在对象初始化的时候相应的虚函数指针就会被替换;
3,虚函数的调用一律通过vtable定位,因为存在vtable这一层中继,就可以保证在运行态可以通过父类的指针执行指向子类对象的方法,因为类对象初始化的时候正确的重写了vtable的内容。
4,一个对象多一个包含virtual function的基类,就会在类变量的结构中多引入一个指向父类vtable structure的指针。在类对象初始化的时候,就需要更多的 vtable 初始化代码。:D

多重继承会导致 vtable 膨胀, Microsoft ATL 引入了一个 ATL_NO_VTABLE __declspec(novtable) C++ 扩展。关于这个,下回再说~~~

其实这个例子里面还有一个小问题, 不知道大家能不能看出来啊!

2009/01/15

Nortel files for bankruptcy

百年老店终于也挺不住了, NT的问题是积重难返,如果没有本质性的改变,估计会就此消失了。即便能恢复回来,估计也就不剩什么了~~~ :(

2008/12/18

VIM is so cool

VIM is really cool, you can increase/decrease a number in the text directly by with CTRL-A and CTRL-X!


Adding and subtracting

*CTRL-A*
CTRL-A Add [count] to the number or alphabetic character at
or after the cursor. {not in Vi}


*CTRL-X*
CTRL-X Subtract [count] from the number or alphabetic
character at or after the cursor. {not in Vi}

The CTRL-A and CTRL-X commands work for (signed) decimal numbers, unsigned
octal and hexadecimal numbers and alphabetic characters. This depends on the
'nrformats' option.
- When 'nrformats' includes "alpha", Vim will change the alphabetic character
under or after the cursor. This is useful to make lists with an alphabetic
index.
- When 'nrformats' includes "hex", Vim assumes numbers starting with '0x' or
'0X' are hexadecimal. The case of the rightmost letter in the number
determines the case of the resulting hexadecimal number. If there is no
letter in the current number, Vim uses the previously detected case.
- When 'nrformats' includes "octal", Vim considers numbers starting with a '0'
to be octal. Other numbers are decimal and may have a preceding minus sign.
If the cursor is on a number, the commands apply to that number; otherwise
Vim uses the number to the right of the cursor.

For numbers with leading zeros (including all octal and hexadecimal numbers),
Vim preserves the number of characters in the number when possible. CTRL-A on
"0077" results in "0100", CTRL-X on "0x100" results in "0x0ff". Note that
when 'nrformats' includes "octal", decimal numbers with leading zeros are
impossible because they are indistinguishable from octal numbers.

The CTRL-A command is very useful in a macro. Example: Use the following
steps to make a numbered list.

1. Create the first list entry, make sure it starts with a number.
2. qa - start recording into buffer 'a'
3. Y - yank the entry
4. p - put a copy of the entry below the first one
5. CTRL-A - increment the number
6. q - stop recording
7. @a - repeat the yank, put and increment times

2008/12/11

Mapping remote TCP port to local via HTTPS Proxy

上次说的Perl代码供大家参考

功能:把远端的应用服务端口通过HTTPS代理服务器映射成本地端口。这对于那些不支持HTTPS代理的TCP应用还有点儿小用处! :D


#!/usr/bin/env perl
#
# Use remote HTTPS PROXY to tunnel the remote service to local!
# Author: Yi Zhao
#   Blog: linuxyz.blogspot.com
#
# Based on original "ssltunnel.pl" by Alex Hornby <alex@hornby.org.uk>
# $Id: ssltunnel.pl,v 1.17 2003/06/10 14:54:16 alex Exp $
#
# This program is free software; you can redistribute it and/or
# modify it under the same terms as Perl itself.
#

package httpsproxy;

use strict;
my $VERSION=1.0;

use IO::File;
use IO::Select;
use IO::Socket;
use Net::SSL;
use Getopt::Long;
use MIME::Base64;

my %options = (
    proxyport=>443,
    reproxyport=>8080,
    localaddr=>"127.0.0.1",
    localport=>8080,
);

sub usage
{
    print STDERR <<EOF;
usage: perl httpsproxy.pl [options] [remote-host:port]
Tunnels a TCP/IP connection through an http proxy using SSL.

WARNING: Only use this if you have the proxy administrator\'s permission
WARNING: The authors of this package offer no warranty

options:
    --help                        This help
    --proxyhost 1.2.3.4           Mandatory proxy host port (default 443)
    --proxyport 443               Optional proxy host port (default 443)
    --proxyuser <username>        Optional proxy user name
    --proxypasswd pass            Optional proxy pass word
    --useragent agent             Optional user agent name
    --reproxyhost 1.2.3.4         Optional intermediate http proxy host
    --reproxyport 123             Optional intermediate http proxy host port (default 8080)
    --reproxyuser <username>      Optional intermediate http proxy user name
    --reproxypasswd pass          Optional intermediate http proxy pass word
    --localaddr 1.2.3.4           Optional local addr to listen on (default 127.0.0.1)
    --localport 123               Optional local port to listen on (default 8080)

e.g. To run a local http proxy to the remote HTTPS proxy

./httpsproxy.pl --proxyhost 10.1.1.80 \
  --proxyport 443 --localport 80  www.abc.com:80

EOF
    exit(1);
}

# Parse command line arguments
sub parseArgs
{
    GetOptions(\%options, qw/dumpfile=s
                   proxyhost=s proxyport=i proxyuser=s proxypasswd=s useragent=s
                   reproxyhost=s reproxyport=i reproxyuser=s reproxypasswd=s reuseragent=s
                   localaddr=s localport=i
                   debug! help!
                   log-file=s pidfile=s/);

    if ( $options{help} ) {
        usage();
    }

    for (@ARGV) {
        if (m/^([^:]*):(.*)$/) {
            $options{desthost} = $1;
            $options{destport} = int($2) || getservbyname($2, 'tcp') || die "unknown port";
            print "Mapping $options{desthost}:$options{destport} as $options{localaddr}:$options{localport}\n";
        }
    }
    
    if ( !defined($options{proxyhost}) ) {
        print STDERR "error: You must give a proxyhost\n";
        usage();
    }
}

# This is really inefficient, but we only use it for reading the proxy response
# so that does not really matter.
sub xgetline($)
{
    my $proxy = shift;
    my $val="";
    my $buf;
    do {
        $proxy->read($buf, 1);
        $val .= $buf;
    } until ($buf eq "\n");

    $val;
}

sub httpProxy
{
    my ( $proxy, $desthost, $destport, $proxyuser, $proxypasswd ) = @_;
    # Force flushing of socket buffers

    # The actual connect
    $proxy->print("CONNECT " .  $desthost . ":" .
                      $destport . " HTTP/1.0\r\n");
    if ( $options{debug} ) {
        print STDERR "CONNECT " .  $desthost . ":" .
                      $destport . " HTTP/1.0\n";
    }

    # Basic auth if needed
    if ( $proxyuser ) {
        my $auth = encode_base64(
            $proxyuser . ":" . $proxypasswd);
        $proxy->print("Proxy-authorization: Basic $auth\r\n");
        if ( $options{debug} ) {
            print STDERR "Proxy-authorization: Basic $auth"
        }
    }

    # User agent name if needed
    if ( $options{useragent} ) {
        $proxy->print("User-Agent: " . $options{useragent} . "\r\n");
        if ( $options{debug} ) {
            print STDERR "User-Agent: " . $options{useragent} . "\n";
        }
    }

    # end of headers
    $proxy->print("\r\n");

    my $status;

    # Wait for HTTP status code, bail out if you don't get back a 2xx code.
    #$_ = $proxy->getline();
    #$_ = $proxy->getchunk();
    $_ = xgetline($proxy);
    next if /^[\r]*$/;
    ($status) = (split())[1];
    die("Received a bad status code \"$status\" from proxy server\n$_")
        if ( int($status/100) != 2 );

    while($_ = xgetline($proxy)) {
        chomp;   # Strip <LF>
        last if /^[\r]*$/;                # Empty line or a single <CR> left

        if ( $options{debug} ) {
            print STDERR "Got extra data [$_]\n";
        }
    }

    return $status;
}

sub connectProxy
{
    if ( $options{reproxyhost} ) {
        # proxy support
        $ENV{HTTPS_PROXY} = qq(http://$options{reproxyhost}:$options{reproxyport});

        # proxy_basic_auth
        $ENV{HTTPS_PROXY_USERNAME} = $options{reproxyuser} if $options{reproxyuser};
        $ENV{HTTPS_PROXY_PASSWORD} = $options{reproxypass} if $options{reproxypass};
    }

    # debugging (SSL diagnostics)
    $ENV{HTTPS_DEBUG} = $options{debug} ? 1 : 0;
  
    my $proxy = new Net::SSL (
        PeerAddr => $options{proxyhost},
        PeerPort => $options{proxyport},
        Proto => 'tcp',
    );

    die "Error connecting to proxy host $options{proxyhost} " .
        "port $options{proxyport}: $!\n" unless $proxy;

    # Force flushing of socket buffers
    $proxy->autoflush(1);

    # only if the remote host are speficied
    httpProxy($proxy, $options{desthost}, $options{destport},
        $options{proxyuser}, $options{proxypasswd} )
    if ( $options{desthost} );

    return $proxy;
}

sub connectLocal
{
    my $listen = new IO::Socket::INET (
        Listen=> 5,
        LocalAddr => $options{localaddr},
        LocalPort => $options{localport},
        Proto => 'tcp',
        Reuse => 1,
    );

    die "can't listen on " . $options{localaddr} . ":"
        . $options{localport} unless $listen;

    print STDERR "Accepting network clients on " .
        $options{localaddr} . ":" .$options{localport} . "\n";

    my %client2proxy;
    my %proxy2client;

    my $s = IO::Select->new();
    $s->add($listen);

    my $dumpfh;
    if ( $options{dumpfile} ) {
        $dumpfh = new IO::File($options{dumpfile}, "w")
            or die "could not open dump file $_";
        $dumpfh->autoflush(1);
    }

    while ( 1 ) {
        my @res = IO::Select::select($s, undef, undef, 3600);
        if ( @res == 0 ) {
            print STDERR "got select error\n";
            last;
        }
        my ($read, $write, $error) = @res;

        # Check for disconnect
        for my $fh ( @$error ) {
            print STDERR "socket $fh is in error\n";
            $s->remove($fh);
            exit();
        }

        # Process handles ready to read;
        for my $fh ( @$read  ) {

            if ( $fh == $listen ) {
                my $client = $listen->accept();
                $client->autoflush(1);
                $s->add($client);
                my $proxy = connectProxy();
                $s->add($proxy);
                print STDERR "New connection from " . $client->peerhost() . "\n";
                $client2proxy{$client} = $proxy;
                $proxy2client{$proxy} = $client;
            } else {
                my $destfh;
                my $isclient = 0;
                if ( exists( $client2proxy{$fh} ) ) {
                    $destfh = $client2proxy{$fh};
                    $isclient = 1;
                } elsif ( exists( $proxy2client{$fh} ) ) {
                    $destfh = $proxy2client{$fh};
                }

                my $num = sysread($fh, $_, 4096);
                if ( $num) {
                    syswrite($destfh, $_, $num);
                    # Optional dump of traffic
                    if ( $dumpfh ) {
                        if ($isclient) {
                            $dumpfh->print("client[$_]\n");
                        } else {
                            $dumpfh->print("proxy[$_]\n");
                        }
                    }
                } else {
                    $s->remove($fh);
                    $s->remove($destfh);
                    if ( $isclient ) {
                        print STDERR "client disconnected\n";
                        delete($client2proxy{$fh});
                        delete($proxy2client{$destfh});
                    } else {
                        print STDERR "proxy disconnected\n";
                        delete($client2proxy{$destfh});
                        delete($proxy2client{$fh});
                    }
                    close($fh);
                    close($destfh);

                    if(%proxy2client == 0 ) {
                        print STDERR "last client disconnected\n";
                    }
                }
            }
        }
    }
}

parseArgs();
connectLocal();

0;

__END__

copy and paste in VIM

VIM have multiple clipboard which allows you copy and save different content at the same time. The register can be any of {a-zA-Z0-9.%#:-"}. It is really interesting thing which I never notice before.

"{a-zA-Z0-9.%#:-"} Use register {a-zA-Z0-9.%#:-"} for next delete, yank
or put (use uppercase character to append with
delete and yank) ({.%#:} only work with put).

:reg[isters] Display the contents of all numbered and named
registers. {not in Vi}

:reg[isters] {arg} Display the contents of the numbered and named
registers that are mentioned in {arg}. For example:

["x]y{motion} Yank {motion} text [into register x]. When no
characters are to be yanked (e.g., "y0" in column 1),
this is an error when 'cpoptions' includes the 'E'
flag.

["x]p Put the text [from register x] after the cursor
[count] times. {Vi: no count}


I forgot there is another register *, it is as same as the system clipboard. So you can yank some text into register *, it will be in the system clipboard also. :D

2008/12/04

Apache HTTPD as Proxy server

由于条件限制,平时网络只能用http代理,其他任何应用都必须通过这个代理。可是这个代理只能支持http以及https应用,不支持CONNECT remote-host:443以外的其他端口,除了浏览网页根本不能用于其它代理。
为此,用Apache自建了一个HTTPS代理,这样就能够利用这个二次代理做一些其他的应用。

Apache HTTPD 真是强悍啊!首先在 httpd.conf 打开mod_proxy;
然后添加下面的语句:


ProxyRequests On
ProxyVia On

Order deny,allow
Deny from all
Allow from .mydomain.com



赶紧试验一下SSH! TLS握手都完成了,貌似就应该能工作了不?

可是实际上不行!:(

每次用 CONNECT 方法来连接服务器的时候总是被403踢下来。感觉应该是访问控制的问题,于是改成没有访问控制;再试过一样403 Forbidden~~~~ 郁闷啊!

看了半天Apache的文档才发现,原来还有一个 AllowCONNECT 指令,并且缺省只打开443和563端口,难怪连22 端口的时候被踢~~~~~

赶紧加上这句:
AllowCONNECT 21 22 23 80 443
再试,Working... 高喊:“Apache 太强悍了~~~”

题外话:这个二次代理的转换程序是用Perl写的,目前还有些小问题,啥时候时候搞好了也放上来!

2008/10/08

健康饮食

说壹千来道壹万,健康生活是正道,
怎么才能活的好?健康饮食最重要。
一日三餐都要吃,早餐万万别省掉!
少吃主食多吃菜,精肉蛋奶不能少,
少食多餐勤运动,零食一定要戒掉。
饮食起居有规律,利国利民身体好!


附食物结构金字塔一个

2008/09/27

关于Google Chrome以及Android

Google Android 对于Google这种依靠高增长率赚钱的公司,如何保持高的增长率是很关键的,Android对于Google来说是开拓新的增长点,这跟当年Microsoft进入报表生成软件领域是一个道理。进入这样的领域所花费的投资,对于Google而言绝对可以忽略,效果则是明显的,就算失败了也不会有什么损失。当然了这次Google跳得有点儿远~~~ 当然了,Google 只用了一年多的时间就能做成这样确实还是很强悍的,虽然大多数东西都是基于已有的技术开发~~~

Google Chrome的感觉有些奇怪,浏览器领域在此之前基本已经尘埃落定,IE保持老大地位,firefox作为老而保持sexy的形象,老三大量的IE内核的克隆产品,然后是Opera以及Safari。从本质上来说,Google应该是不关心浏览器的,但是Microsoft开始进入Google的领域,说实话,谁都要提防Microsoft自说字画的搞乱浏览器市场。Google培育Mozilla就是这样的目的,可以说只要Mozilla没有走到绝对优势的地位,Google就不会停止对Mozilla的支持。当然了这次Google自己赤膊上阵恐怕也抱着同样的目的,那就是:在浏览器市场纠缠Microsoft,增加话语权,同时让Microsoft走到W3C的标准圈子内,不论是Microsoft的Silverlight,还是Adobe的Flash/Flex/Air。 对Google来说,都不是他想看到的,对于Google这种Internet信息服务提供者来说,最好在客户端领域是群雄争霸,决不能一枝独秀。另一方面Chrome真正目的应该是成为Google的桌面应用平台,看看Chrome强调的JavaScript速度,独立进程管理,哪个都像是在给桌面应用开发作准备。

总的来说,Google作为后来者,她要做的就是不断搞出新的东西,不断进入新的Internet或者信息服务相关的外延领域。不论成功或失败,总要在别人的家里打仗才好。

2008/09/26

VIM Tips

I am running in a English version Windows XP in office. The default encoding of the OS is english! While I still want to be able to work with some Chinese document in VIM, how can I make it happen?
That's simple, put this line into your vimrc file
set guifont=Bitstream\ Vera\ Sans\ Mono:h10:cANSI
set guifontwide=NSimSun:h11:cGB2312

VIM will be using NSimSun to display the Chinese characters. :)
And "Bitstream Vera Sans Mono" to be used for ANSI characters.

Indeed this option can be set locally for each individual files by using the VIM modeline
vim:ts=4:sw=4:expandtab:enc=utf8
All the VIM option can be changed locally. Don't forget to put this modeline into the comments :D

VIM is fantastic cool~~~

2008/09/23

强力推荐JavaScript 高级教程

超级牛人 John Resig (在 Mozilla.org 工作,jQuery的作者) 捉刀制作!!! Web 开发必读~~~

Learning Advanced JavaScript
1) Our Goal
2) Defining Functions
3) Named Functions
4) Functions as Objects
5) Context
6) Instantiation
7) Flexible Arguments
8) Closures
9) Temporary Scope
10) Function Prototypes
11) Instance Type
12) Inheritance
13) Built-in Prototypes
14) Enforcing Function Context
15) Bonus: Function Length

2008/08/28

逐鹿蓝天

《逐鹿蓝天》 —— 美国民航业的经营管理

Web 2.0

以前一直对所谓的 Web2.0 不敢冒, 主要还是因为对 Web2.0 的概念不了解。 今天在 西西河 看到铁手老大的帖子: 对Web2.0的描述简明扼要,重点突出,很有感觉

一般而言,谈论WEB2.0时,我们的概念基本上是,1、用户贡献的内容。2、方便的交互环境。和以前的网站概念不同,WEB2.0主要是依靠用户的参 与。用户的直接参与和内容提供,这是大家都能看到的WEB2.0的核心要素。好的WEB2.0,是在于能够有比较清楚的定位,吸引特定的人群,并在技术上 方便用户的参与。比如MYSPACE更注重社交功能,三教九流,五花八门都可以找到或者建立自己的朋友圈子,内容并不重要。
从这个意义上说,digg.com del.icio.us 才有那么点儿Web2.0的意思。 :)

BlockChain 相关电子书

@copyright of Sam Chadwick   - https://thehub.thomsonreuters.com/groups/bitcoin/blog/2017/09/10/blockchain-paper Blockchain Papers A c...