read more!
Monday, April 5, 2010
Repetition of an old post
In 2008 I've written a post about interesting security technique. Then, I've removed it exactly until April and I know that no more than one person was able to read it and that it completely disappeared from the network. I now reminded myself about the technique. I found it quite useful. It's about safety. Basically, there are threats that require extremely sophisticated conditions to fully arise. When you defend yourself from them, you may find it playful. You may even find your self-value to rise. But then, there are threats that aren't so sophisticated. They can basically always catch you. This is the time to return to the ground. It's the social engineering! So how to defend from it? In my opinion there is only one answer: be aware of the consequences of your actions, and take into account possible actions of the people that you share your safety with. Read more here.
read more!
Posted by Mariusz Gniazdowski at 7:09 AM 0 comments
Tuesday, March 17, 2009
Avoiding pointers
I often see a C++ code that uses pointers in situations, where they're not needed. It seems that we often easily give up when we encounter slightly irregular code construct, where typical reference usage is not obvious. Consider following situation:
class A {
public:
virtual void action() = 0;
};
class B : public A {
public:
B() {}
void action() { /* action code */ }
};
class HolderClass {
public:
void setInstance(A * newInstance) {
instance = newInstance;
}
void doSomething() {
instance->action();
}
private:
A * instance;
};
int main() {
B myInstance;
HolderClass c;
c.setInstance(&myInstance);
}
The general rule is: to avoid pointers, allow the compiler to arrange things in RAII way. Use references, initialize them as fast as you can (i.e. in base initializers):
class A {
public:
virtual void action() = 0;
};
class B : public A {
public:
B() {}
void action() { /* action code */ }
};
class HolderClass {
public:
HolderClass(A & newInstance) : instance(newInstance) {}
void doSomething() {
instance.action();
}
private:
A & instance;
};
int main() {
B myInstance;
HolderClass c(myInstance);
}
However, both of above approaches share the same issue: the ownership issue. Consider following scenario:
HolderClass* fun() {
B myInstance;
HolderClass* c = new HolderClass(myInstance);
/* Or:
HolderClass* c = new HolderClass();
c->setInstance(&myInstance);
*/
return c;
}
Possible pointer-approach solutions are:
- Use shared pointer instead of regular pointer.
- Take a pointer and copy the object, storing pointer to newly created instance.
But how to solve this without using pointers? Generally, we must copy the object before binding it to the reference member. If A would not have been an abstract class, and the C++0x standard Rvalue references would have been already available, then following solution would be possible:
class HolderClass {
public:
HolderClass(A & newInstance) : instance(A(newInstance)) {
}
private:
A && instance;
};
But A is an abstract class, and we may not want to use unfinished standard features. Is it possible to make a copy of A* in such a way, that it would be available in base initializer list? It is! Thanks to the fact, that you can bind (after dereferencing) pointer returned by new() to an reference variable. Below you can see two possible solutions:
class A {
public:
virtual void action() = 0;
};
class B : public A {
public:
B() {}
void action() { }
};
class C : public A {
public:
B() {}
void action() { }
};
A & copyOf(A & a) {
if( typeid(a) == typeid(B)) {
B * b = new B( *dynamic_cast<B*>(&a) );
return *b;
} else if( typeid(a) == typeid(C)) {
C * c = new C( *dynamic_cast<C*>(&a) );
return *c;
}
}
class HolderClass {
public:
HolderClass(A & newInstance) :
instance(copyOf(newInstance)) {}
~HolderClass() { delete &instance; }
void doSomething() {
instance.action();
}
private:
A & instance;
};
int main() {
B myInstance;
HolderClass c(myInstance);
}
Next solution follows the virtual copy constructor idiom:
class A {
public:
...
virtual A& clone() = 0;
...
};
class B : public A {
public:
...
virtual A& clone() { return *new B(*this); }
...
};
class HolderClass {
public:
HolderClass(A& newInstance) :
instance(newInstance.clone()) {}
~HolderClass() { delete &instance; }
void doSomething() {
instance.action();
}
private:
A& instance; // this can be A&&, A&, A*,
// auto_ptr<A>, etc (any of them would work in your
// case)
};
Notice the delete calls in ~HolderClass() destructors — binding to an reference variable doesn't have anything to do with managing of memory lifetime.
The copyOf() approach is non-intrusive and can be easily used with third-party classes which cannot be modified. Otherwise the clone() approach is probably cleaner.
read more!
Posted by Mariusz Gniazdowski at 12:16 PM 0 comments
Friday, October 17, 2008
Most useless use of ZSH
I found neat ZSH hack:
What do you think this function does?
1 function most_useless_use_of_zsh {
2 local lines columns colour a b p q i pnew
3 ((columns=COLUMNS-1, lines=LINES-1, colour=0))
4 for ((b=-1.5; b<=1.5; b+=3.0/lines)) do
5 for ((a=-2.0; a<=1; a+=3.0/columns)) do
6 for ((p=0.0, q=0.0, i=0; p*p+q*q < 4 && i < 32; i++)) do
7 ((pnew=p*p-q*q+a, q=2*p*q+b, p=pnew))
8 done
9 ((colour=(i/4)%8))
10 echo -n "\\e[4${colour}m "
11 done
12 echo
13 done
14 }
It draws Mandelbrot fractal :D This is possible because of ZSH floats support.
read more!
Posted by Mariusz Gniazdowski at 12:45 AM 0 comments
Labels: zsh
Monday, March 10, 2008
Comfortable command line in Java
Readline is well known GNU library that provides comfortable command line in text environment. It can be very easily used with C and C++, but many problems arise when trying to use it with Java. Readline is binary, platform dependant library. Using it with Java needs lots of hacking to preserve some platform independence and is problematic when targeting Windows platform. Readline is also licensed under GPL and any program linking with it must have compliant license. Recently I was developing command line application which had to run under Linux and Windows as well. I was trying to use java-readline, but it didn’t support Windows. I then found other library, which is written in pure Java: JLine.
JLine is small, flexible Java library for handling console input. Feature highlights include:
- command line editing (you can use arrows to move over entered text, etc.),
- history of entered commands,
- completion (also filenames!).
Below you can see example demonstrating JLine flexibility, simplicity and power.
import jline.*;Basically each line in below ends with TAB key pressed, which causes JLine to generate proper completion.
import java.io.*;
import java.util.*;
public class Cmdline {
public static void main(String[] args) throws IOException {
ConsoleReader reader = new ConsoleReader();
reader.setBellEnabled(false);
List argCompletor1= new LinkedList();
argCompletor1.add(new SimpleCompletor(new String[] { "ls", "mkdir" }));
argCompletor1.add(new FileNameCompletor());
List argCompletor2 = new LinkedList();
argCompletor2.add(new SimpleCompletor(new String[] {"ps"}));
argCompletor2.add(new SimpleCompletor(new String[] {"-ax",
"-axu","--help"}));
List completors = new LinkedList();
completors.add(new ArgumentCompletor(argCompletor1));
completors.add(new ArgumentCompletor(argCompletor2));
reader.addCompletor(new MultiCompletor(completors));
String line;
PrintWriter out = new PrintWriter(System.out);
while ((line = reader.readLine("READY # ")) != null) {
out.println("::" + line );
out.flush();
if (line.equalsIgnoreCase("quit") ||
line.equalsIgnoreCase("q"))
break;
}
}
}
# java -cp jline-0.9.93.jar:. CmdlineMore information:
READY #
ls mkdir ps
READY # ls /
_darcs bin boot dev etc fonts
home lib lost+found media mnt opt
proc root sbin sys tmp usr
var
READY # ls /mnt/c
camera cdrom cdromaes
READY # ps -
--help -ax -axu
READY # ps -ax
-ax -axu
READY # mkdir
Cmdline.class Cmdline.java jline-0.9.93.jar
READY # mkdir /
_darcs bin boot dev etc fonts
home lib lost+found media mnt opt
proc root sbin sys tmp usr
var
- http://java-readline.sourceforge.net/
- http://jline.sourceforge.net/
read more!
Posted by Mariusz Gniazdowski at 4:53 PM 1 comments
Wednesday, January 30, 2008
Zsh unique features
My favorite shell is The Z Shell. It has many features that can't be found in Bash, for example hash tables:
#!/bin/zsh
typeset -A myArray
myArray[someKey]=firstValue
myArray[otherKey]=secondValue
echo $myArray[someKey] , $myArray[otherKey]
Using hash tables is very easy in Zsh. In Bash you can only emulate hashes.
Another unique Zsh feature is zparseopts. Look at following example:
#!/bin/zsh
zmodload zparseopts
zparseopts -D -E -A Args -- a b -aopt -bopt
if (( ${+Args[-a]} )); then
echo "option -a given";
fi
if (( ${+Args[-b]} )); then
echo "option -b given";
fi
if (( ${+Args[--aopt]} )); then
echo "long option --aopt given";
fi
if (( ${+Args[--bopt]} )); then
echo "long option --bopt given";
fi
if [ "$#@" -gt 0 ]; then
echo Non option arguments are: "$@"
fi
Example outputs of this script:
# ./parseex -a -b
option -a given
option -b given
# ./parseex -a x y --bopt
option -a given
long option --bopt given
Non option arguments are: x y
# ./parseex -a x y --bopt -a
option -a given
long option --bopt given
Non option arguments are: x y
# ./parseex -ab x y --bopt z --aopt z
option -a given
option -b given
long option --aopt given
long option --bopt given
Non option arguments are: x y z z
Notice how extremely easy it is to parse command line options given in not straightforward form! Zparseopts will parse "-ab" as "-a -b" and "-a text -b text2" as "-a -b text text2"! Scripts written using zparseopts behave like normal console applications, because advanced command line options allow comfortable script invocation.
read more!
Posted by Mariusz Gniazdowski at 12:35 PM 0 comments
Subscribe to:
Posts (Atom)