Sep 28, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Problem 8.11 and register/2

Hi Bryan: I’m not even sure that this is testable since it would involve testing for the non-existence of a race condition. Formal verification is possible since Erlang uses CSP (Communicating Sequential Processes). I’m not sure how it is done, but it is possible to prove the correctness of code like this.

A design pattern does exist and is implemented in the distribution: the OTP behaviours all do this transactional spawn and register using gen:start/6. The code for that is (excerpt from Erlang/OTP R12-B Source for gen.erl):

start(GenMod, LinkP, Name, Mod, Args, Options) ->
    case where(Name) of
    undefined ->
        do_spawn(GenMod, LinkP, Name, Mod, Args, Options);
    Pid ->
        {error, {already_started, Pid}}
    end.

The real answer to Peter’s Question 2 is that this is a theoretical problem unlikely to appear in a practical Erlang/OTP system. If you are using registered processes, you are in all likelihood using OTP behaviours which manage the transactional semantics for you. A reasonable Erlang/OTP system would not attempt to register the same name twice. Registered names work best for persistent server processes and these are: 1) hard to write correctly, and 2) already written correctly and battle tested in OTP.

 
Sep 21, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Simple and free Windows/Erlang editor

TextMate/E Text Editor (non-free but worth it):
TextMate on Mac OS X and E Text Editor on Windows are very good easy to use editors. Despite many out of the box limitations for Erlang I find TextMate/E Text Editor very easy to customize and have added dynamic code compile and code completion support (very buggy right now). TextMate is my editor of choice and E Text Editor is basically identical (including support for TextMate bundles).

Vim:
Vim is decent for Erlang and the Windows version is pretty easy to use out of the box. The syntax highlighting is flawed though: does not handle $” properly for example. I use Vim for Erlang when I am running Linux.

Emacs:
The standard Erlang IDE is Emacs. I personally have not used Emacs for Erlang so I cannot recommend it further.

ErlIDE:
Have not tried it yet. I will give it a spin and see how it turns out.

 
Sep 17, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Loops and accumulated data

A functionally equivalent module using module-level functions and guards:


-module(crc16).
-export([calculate/1]).

%%% CRC16 CCITT Normalized Polynomial
-define(POLYNOMIAL, 16#1021).

calculate(X) -> calculate(8, X).

calculate(0, X) -> X;
calculate(N, X) when X band 16#0001 == 1 ->
    calculate(N-1, ?POLYNOMIAL bxor (X bsr 1));
calculate(N, X) ->
    calculate(N-1, X bsr 1).

I find that using module-level functions and guards is often more readable than using if statements and anonymous functions. It avoids a lot of syntactical weirdness as well.

 
Sep 16, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / getting error on starting chat-client: lib_md5 missing?

Thank you Barry. Your solution makes more sense. I was unfamiliar with using Make with Erlang when I originally posted. Now I use it all the time :)

 
Jul 24, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Discount for bulk purchases?

This should be listed on http://www.pragprog.com/frequently-asked-questions/volume-discounts but it is unfortunately not.

They may not see your request here so I please contact sales@pragprog.com for more information.

 
Jul 24, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / MinGW: where can I find it?

An Erlang Installer for Windows is available from http://erlang.org/download.html

The MinGW installer is made available through SourceForge at http://sourceforge.net/project/showfiles.php?group_id=2435&package_id=240780&release_id=595197

MSYS is made available through SourceForge at http://sourceforge.net/project/showfiles.php?group_id=2435

I have had success with Cygwin (http://www.cygwin.com/), but have never tried MinGW, so I recommend trying Cygwin if this fails.

 
Jul 24, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / MinGW: where can I find it?

An Erlang Installer for Windows is available from http://erlang.org/download.html

The MinGW installer is made available through SourceForge at http://sourceforge.net/project/showfiles.php?group_id=2435&package_id=240780&release_id=595197

MSYS is made available through SourceForge at http://sourceforge.net/project/showfiles.php?group_id=2435

I have had success with Cygwin (http://www.cygwin.com/), but have never tried MinGW, so I recommend trying Cygwin if this fails.

 
Jul 16, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Episode 5: Code Style Debate

analyze/1 written using if expression:

analyze(N) ->
  if
    N rem 15 == 0 ->
      fizzbuzz;
    N rem 5 == 0 ->
      buzz;
    N rem 3 == 0 ->
      fizz;
    true ->
      N
  end.

analyze/1 written using pattern matching and guards:

analyze(N) when N rem 3 =:= 0 andalso N rem 5 =:= 0 -> fizzbuzz;
analyze(N) when N rem 3 =:= 0 -> fizz;
analyze(N) when N rem 5 =:= 0 -> buzz;
analyze(N) -> N.

generate_sequence/2 written using a case expression:

generate_sequence(Pid, N) ->
  case is_number(N) of
    false ->
      exit({badarg, N});
    true ->
      Pid ! {generate, self(), N},
      receive
        {ok, Result} ->
          Result
        after 1000 ->
          {error, timeout}
      end
  end.

generate_sequence/2 written using pattern matching and guards:

generate_sequence(Pid, N) when is_integer(N) ->
  Pid ! {generate, self(), N},
  receive
    {ok, Result} ->
      Result
    after 1000 ->
      {error, timeout}
  end;
generate_sequence(_, N) -> exit({badarg, N}).

generate_fizzbuzz_list/1 written using explicit recursion:

generate_fizzbuzz_list(N) ->
  generate_fizzbuzz_list(1, N, []).

generate_fizzbuzz_list(Pos, N, Accum) when Pos =< N ->
  generate_fizzbuzz_list(Pos + 1, N, lists:append(Accum, [analyze(Pos)]));
generate_fizzbuzz_list(Pos, N, Accum) when Pos > N->
  Accum.

generate_fizzbuzz_list/1 written using list comprehensions:

generate_fizzbuzz_list(N) ->
  [analyze(Value) || Value <- lists:seq(1, N)].

What do you think?

 
Jul 15, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Topics for Future Episodes

Use of make would be cool too. I copy the standard Makefile and support scripts from mochiweb every time I create a new Erlang project now. This could almost be an aside since it is so easy to keep working once it is in place.

I have made TextMate run make when I save and display a dialog of errors or warnings linked to the corresponding lines in source files. If there are no errors/warnings the dialog is not shown.

 
Jul 15, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Topics for Future Episodes

I think EDoc would be a good topic to cover. Documentation is a hugely important and often forgotten part of collaborative development efforts.

 
Jul 15, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / How do I get EUnit?

I solved this by going into Terminal and typing the following:
svn co http://svn.process-one.net/contribs/trunk/eunit eunit

cd eunit
make
cd ..
sudo mv eunit /opt/local/lib/erlang/lib/eunit-2.0b1

After this EUnit was available for me to continue Episode 5. Dropping a library folder — like eunit — containing an ebin into erlang/lib appears to function like dropping a JAR in a Java ext directory.

 
Jul 14, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / How do I get EUnit?

My Erlang distribution did not include EUnit. I am using MacPorts Erlang/OTP R12B-2. Is EUnit part of Erlang/OTP or is it a separate install?

 
Jul 11, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Erlang for loop pg.56

I ran into this exact same problem.

That function definition syntax is only valid at in a module file which you would compile and load.

The book has a warning there about that, but it is unfortunately two pages later under the heading “Common Errors”.

Erlang expressions written in EShell have the same syntax rules as those within the body of a function within a module file. As a result you cannot define functions this way in EShell.

I hope this helps. Thank you for posting your question.

 
Jul 11, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Topics for Future Episodes

I vote for an episode or set of episodes covering a refactor to OTP of the chat system :)

 
Jul 4, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Erlang in Practice / Omission in Episode 1

Good point. A little spoiler note: that error is deliberate. Watch screencast 2 for the resolution.

 
Jun 21, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Matter of style and efficiency

Hi Frank,

Thank you for this interesting post. It raises some very important questions and issues to keep in mind when writing Erlang code.

In the book odds_and_evens_acc/3 is written the way it is to allow tail-recursive optimization of the call stack. This sounds like a terrible reason to structure your code, but it is essential for scalability to arbitrarily large lists. It is a core concept to writing Erlang code.

Your odds_and_evens_acc_v2/1 makes use of the result of a recursive call within the recursive function. This forces the Erlang runtime to maintain a growing stack for each recursion (similar to Java/C++). This does not scale as it will eventually exhaust available memory for a large enough list.

Your version of filter/2 makes use of the result of a recursive call in the append/2 call. This means it will also not scale to large lists. The case-version of filter/2 in the book is much clearer than the doubly-recursive version in the book.

Your post raised some very important issues about Erlang coding. Thank you for posting :)

 
Jun 15, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Chapter 8 Problems

Hi Nico,

You have an interesting and concise solution there. I like the idea of having a single different process in the ring that decrements the message number. Nice work!

 
May 7, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / unix crypt() fun

OTP R12B includes the Crypto Application:
http://www.erlang.org/doc/apps/crypto/index.html

I’m not sure how complete it is. My understanding is that ejabberd includes a more complete OpenSSL implementation which they need for SSL Jabber/XMPP.

 
May 7, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Erlang Python Example

Very nice Stephan. Thank you for posting that. I was looking for a cleaner way to do communication between Erlang and Python. I could not figure out how to make Python implementation for the ports example.

Until now I have been using TCP/IP line-based communication. I could not figure out how to get the packet size thing to work. If you are interested I have included my old approach below.

TCP line-based integration with Erlang:

-module (echo_server).
-export([start/0]).

start() ->
    {ok, Listen} = gen_tcp:listen(4321, [list, {packet, line},
                                         {reuseaddr, true},
                                         {active, true}]),
    spawn(fun() -> par_connect(Listen) end).

par_connect(Listen) ->
    {ok, Socket} = gen_tcp:accept(Listen),
    spawn(fun() -> par_connect(Listen) end),
    io:format("Client connected~n"),
    echo(Socket). 

echo(Socket) ->
    receive
        {tcp, Socket, Line} ->
            gen_tcp:send(Socket, Line),
            echo(Socket);
        {tcp_closed, Socket} ->
            io:format("Client disconnected~n")
    end.

Telnet can then be used to test the interface: telnet 127.0.0.1 4321. Once you are satisfied it is very easy to build a TCP client in Python. I used this to implement a very basic Erlang code completion server for use with TextMate.

 
May 7, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Some question about Chapter.14 (How to execute string)

lib_misc:string2value/1 is implemented as follows:

string2value(Str) ->
    {ok, Tokens, _} = erl_scan:string(Str ++ "."),
    {ok, Exprs} = erl_parse:parse_exprs(Tokens),
    Bindings = erl_eval:new_bindings(),
    {value, Value, _} = erl_eval:exprs(Exprs, Bindings),
    Value.

I could not find a direct equivalent to Python’s exec statement in the modules shipped with Erlang OTP R12B.

The entire set of example code for Programming Erlang is available for download here:
http://www.pragprog.com/titles/jaerlang/source_code

 
Apr 2, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Erlang control Java?

If you use open_port({spawn, "command"}, [stream]) you will be able to use standard IO streams on the Java side and message send and receive operations on the Erlang side. There is also a line option which might be useful. Just make sure to use a PrintWriter or some other buffered output stream and call flush() from the Java side to send a message.

An Erlang module to dump content into the Mac OS X clipboard using the pbcopy program:

copy(Data) ->
    Clipboard = open_port({spawn, "pbcopy"}, [stream]),
    Clipboard ! {self(), {command, Data}},
    Clipboard ! {self(), close},
    receive
        {Clipboard, closed} -> true
    end.

If you bring up the Erlang docs for open_port on http://www.gotapi.com/ it explains how to communicate with the port.

 
Apr 2, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / RSA encryption

Take a look at the ejabberd libraries http://www.ejabberd.im/

The ejabberd guys implemented SSL and a bunch of other very useful libs for Erlang.

CEAN http://cean.process-one.net/packages/ and Jungerl http://jungerl.sourceforge.net/ are decent sources for stuff like this as well. Jungerl is not for the feint of heart, but they have a lot of projects for wrapping the best of breed GNU and BSD libraries.

 
Apr 2, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Chapter 8 Problems

I posted a reply to your blog, but it was dark and appears to have been eaten by a grue :(

 
Apr 2, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / Side effect

My understanding (Joe, correct me if I am wrong), is that the term Side effect is used in the book to mean anything that alters state outside of the current function being executed.

All Variables in Erlang are either bound or unbound. Once bound through matching in an expression an Erlang Variable cannot be changed. What appears to be an assignment operator (the ”=” sign) is in actual fact a constraint expression declaring the left and right hand sides of the expression to be equal.

Writing X = 1 followed by X = 2 will fail on X = 2 because X has already been constrained to equal 1 by X = 1. This pattern matching mechanism requires rethinking the design of state and variables in a program. IMHO, the end result is more comprehensible code that is easier to reason about and explain to others.

In Erlang an expression cannot directly modify the state of another function or even other expressions in the same scope. All such modifications are explicitly made through the interpretation of messages or function parameters. By Chapter 3 you have not gotten to see Message Passing or Concurrency. It should hopefully be clearer at that point.

I check this board frequently so please post your questions here. I will do my best to help :)

 
Apr 2, 2008
Alain_o_dea_small Alain O'Dea 35 posts

Topic: Programming Erlang / E is for excellent: Appendix E

Don’t forget to read Appendix E. It explains many of the tools that come with Erlang like Code Coverage, Profiler, and Cross-reference analyzers.

It also gives a quick overview of the Debugger and debugging technique, provides some explanation of the errors the Compiler generates, and explains how to use the Tracing tool.

Seriously, read Appendix E. It takes Erlang programming from a design exercise to a seriously pragmatic and productive endeavor. I went from running mind-experiments of my code to doing unit testing with coverage analysis within an hour of skimming over Appendix E.

These tools are all invoked using Erlang code. This makes automating workflows that use them surprisingly easy and convenient.

A module called project which I created to handle builds and coverage for a game server I am writing:

-module(project).
-author('alain.odea').
-license('http://opensource.org/licenses/afl-3.0.php').
-export([make/0, cover/0]).

each(Fun) ->
    lists:map(Fun, [actor, escrow, game, hex, inner_perimeter, 
                    intersection, outer_perimeter, path, player,
                    server, status, stockpile, test_game]).

make() ->
    each(fun(Mod) -> shell_default:c(Mod, [debug_info]) end).

cover() ->
    cover:start(),
    each(fun cover:compile/1),
    test_game:run(),
    each(fun cover:analyse_to_file/1).

35 posts

Page: 1 2