100% found this document useful (3 votes)
54 views55 pages

Download Complete Decompiling Java Nolan Godfrey PDF for All Chapters

Nolan

Uploaded by

osoweladu
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
100% found this document useful (3 votes)
54 views55 pages

Download Complete Decompiling Java Nolan Godfrey PDF for All Chapters

Nolan

Uploaded by

osoweladu
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 55

Experience Seamless Full Ebook Downloads for Every Genre at textbookfull.

com

Decompiling Java Nolan Godfrey

https://textbookfull.com/product/decompiling-java-nolan-
godfrey/

OR CLICK BUTTON

DOWNLOAD NOW

Explore and download more ebook at https://textbookfull.com


Recommended digital products (PDF, EPUB, MOBI) that
you can download immediately if you are interested.

Agile Swift: Swift Programming Using Agile Tools and


Techniques Godfrey Nolan

https://textbookfull.com/product/agile-swift-swift-programming-using-
agile-tools-and-techniques-godfrey-nolan/

textboxfull.com

Writing for University Godfrey

https://textbookfull.com/product/writing-for-university-godfrey/

textboxfull.com

Fire Pump Arrangements at Industrial Facilities Nolan

https://textbookfull.com/product/fire-pump-arrangements-at-industrial-
facilities-nolan/

textboxfull.com

Intelligence Analysis Fundamentals 1st Edition Godfrey


Garner

https://textbookfull.com/product/intelligence-analysis-
fundamentals-1st-edition-godfrey-garner/

textboxfull.com
Statistics for the Behavioral Sciences 4th Edition Susan
A. Nolan

https://textbookfull.com/product/statistics-for-the-behavioral-
sciences-4th-edition-susan-a-nolan/

textboxfull.com

Nolan Black Hearts MC 3 1st Edition Ruth Colby [Colby

https://textbookfull.com/product/nolan-black-hearts-mc-3-1st-edition-
ruth-colby-colby/

textboxfull.com

Why You Like It The Science and Culture of Musical Taste


Nolan Gasser

https://textbookfull.com/product/why-you-like-it-the-science-and-
culture-of-musical-taste-nolan-gasser/

textboxfull.com

Hemingway’s Geographies: Intimacy, Materiality, and Memory


1st Edition Laura Gruber Godfrey (Auth.)

https://textbookfull.com/product/hemingways-geographies-intimacy-
materiality-and-memory-1st-edition-laura-gruber-godfrey-auth/

textboxfull.com

Business Networks in East Asian Capitalisms. Enduring


Trends, Emerging Patterns 1st Edition Jane Nolan

https://textbookfull.com/product/business-networks-in-east-asian-
capitalisms-enduring-trends-emerging-patterns-1st-edition-jane-nolan/

textboxfull.com
Decompiling Java
GODFREY NOLAN

APress Media, LLC


Decompiling Java
Copyright © 2004 by Godfrey Nolan
Originally published by Apress in 2004
Softcover reprint of the hardcover 1st edition 2004
Lead Editor: Gary Cornell
Technical Reviewer: John Zukowski
Editorial Board: Steve Anglin, Dan Appleman, Ewan Buckingham, Gary Cornell, Tony Davis,
John Franldin, Jason Gilmore, Chris Mills, Steve Rycroft, Dominic Shakeshaft, Jim Sumser,
Karen Watterson, Gavin Wray, John Zukowski
Project Manager: Tracy Brown Collins
Copy Edit Manager: Nicole LeClerc
Copy Editor: Rebecca Rider
Production Manager: Kari Brooks
Production Editor: Katie Stence
Proofreader: Linda Seifert
Compositor and Artist: Kinetic Publishing Services, LLC
Indexer: Rebecca Plunkett
Cover Designer: Kurt Krames
Manufacturing Manager: Tom Debolski

Ubrary of Congress Cataloging-in-Publicatlon Data


Nolan, Godfrey.
Decompiling Java I Godfrey Nolan.
p.cm.
Includes index.
ISBN 978-1-4302-5469-0 ISBN 978-1-4302-0739-9 (eBook)
DOI 10.1007/978-1-4302-0739-9
1. Java (Computer program language) 1. TitIe.
QA76.73.J38N65 2004
005.13'3-dc22 2004014051

AU rights reserved. No part of this work may be reproduced or transmitted in any form or by any
means, electronic or mechanical, including photocopying, recording, or by any information storage
or retrieval system, without the prior written permission of the copyright owner and the publisher.
Printed and bound in the United States of America 9 8 7 6 5 4 3 2 1
Trademarked names may appear in this book. Rather than use a trademark symbol with every
occurrence of a trademarked name, we use the names only in an editorial fashion and to the
benefit of the trademark owner, with no intention of infringement of the trademark.

The information in this book is distributed on an "as is" basis, without warranty. Although every
precaution has been taken in the preparation of this work, neither the author(s) nor Apress shall
have any liability to any person or entity with respect to any 10ss or damage caused or alleged to
be caused directly or indirectly by the information contained in this work.
In memory ofHanpeter Van Vliet
Contents at a Glance
About the Author ................................................... ix
About the Technical Reviewer ..................................... xi
Acknowledgments ................................................... xiii

Chapter 1 Introduction ......................................... 1


Chapter 2 Ghost in the Machine ............................... 17
Chapter 3 Tools of the Trade ................................. 61
Chapter 4 Protecting Your Source: Strategies for
Defeating Decompilers .............................. 79
Chapter 5 Decompiler Design ................................. 121
Chapter 6 Decompiler Implementation ........................ 159
Chapter 7 Case Studies ....................................... 237
Appendix Classfile Grammar ................................. 247

Index ..................................................... ......... 255

v
Contents
About the Author ................................................... ii
About the Technical Reviewer ..................................... xi
Acknowledgments ................................................... xiii

Chapter 1 Introduction ....................................... 1


Compilers and Decompilers ......................................... 2
Virtual Machine Decompilers ....................................... 3
Why Java? ..................................................... ...... 3
History: Basic Chronology ......................................... 6
Legal Issues ..................................................... ... 9
Moral Issues ..................................................... .. 12
Protecting Yourself ............................................... 13
Book Outiine ..................................................... .. 15
Conclusion ..................................................... .... 16

Chapter 2 Ghost in the Machine .......................... . 17


The JVM: An Exploitable Design? ................................. 18
Inside a Class file ................................................ 22
Conclusion ..................................................... .... 60

Chapter 3 Tools of the Trade .............................. 61


Employing Hexadecimal Editors ................................... 61
The Problem of Insecure Code .................................... 64
Disassemblers ..................................................... . 67
Decompilers ..................................................... ... 72
Obfuscators ..................................................... ... 75
Conclusion ..................................................... .... 76

vii
Contents

Chapter 4 Protecting Your Source: Strategies


for Defeating Decompilers .................... 79
Compilation Flags ................................................. 81
Writing Two Versions of the Applet or Application ............ 86
Employing Obfuscation ............................................. 88
Web Services and Server-Side Execution ....................... . 106
Encryption ........................................................ 108
Digital Rights Management ...................................... . 109
Fingerprinting Your Code ....................................... . 110
Selling the Source Code ......................................... 117
Native Methods ................................................... 117
Conclusion ........................................................ 119

Chapter 5 Decompiler Design .............................. 121


Introduction ...................................................... 122
Defining the Problem ............................................. 125
(De)Compiler Tools ............................................... 128
Strategy .......................................................... 141
Parser Design ..................................................... 149
Conclusion ........................................................ 157

Chapter 6 Decompiler Implementation .................... 159


ClassToXML Output: An Overview ................................. 159
Jlex Specification ............................................... 165
CUP Specification ................................................ 170
Test Suite ....................................................... . 182
Summarizing Decompiler Implementation ......................... 233
Conclusion ........................................................ 236

Chapter 7 Case Studies ..................................... 237


Case Studies ...................................................... 237
Conclusion ........................................................ 244

Appendix Class file Grammar .............................. 247

Index ............................................................ . 255

viii
About the Author
Godfrey Nolan is President of RIIS LLC, where he specializes in web site
optimization. He has written numerous articles for different magazines and
newspapers in the US, the UK, and Ireland. Godfrey has had a healthy obsession
with reverse engineering bytecode ever since he wrote "Decompile Once, Run
Anywhere," which first appeared in Web Techniques in September 1997.

ix
About the
Technical Reviewer
John Zukowski is a freelance writer and strategic Java consultant for JZ Ventures,
Inc. His latest endeavor is to create a next-generation mobile phone platform
with SavaJe Technologies. Look for the 1.5 edition of his Definitive Guide to
Swing for Java 2 in the fall of 2004 (also published by Apress}.

xi
Acknowledgments
THERE ARE COUNTLESS PEOPLE I have to thank in some small way for helping me
with this book. Apologies if I've forgotten anyone.

• My wife, Nancy, and also my children, Rory and Dayna, for putting up with
all the times I've missed a family outing while writing this book. And we're
talking lots and lots of missed outings.

• Jonathon Kade, for all your hard work helping with the decompiler and
Chapter 6 in general.

• Gary Cornell, without whom this book would never have seen the light
of day.

• Tracy Brown Collins and Rebecca Rider at Apress, for putting up with my
countless missed deadlines. Do I need to say lots and lots again?

• John Zukowski, for all the helpful comments. And yes, I'm still ignoring the
one about having a comma in Hello World.

• Dave and Michelle Kowalske and all my other in-laws, for knowing when
not to ask, "Is that book finished yet?"

• Finally, to my parents, who have always taught me to aim high and who
have supported me when, more often than not, I fell flat on my face.

xiii
CHAPTER 1

Introduction
WHEN COREL BOUGHT WordPerfect for almost $200 million from the Novell
Corporation in the mid 1990s, nobody would have thought that in a matter of
months they would have been giving away the source code free. However, when
Corel ported WordPerfect to Java and released it as a beta product, a simple
program called Mocha1 could quickly and easily reverse engineer, or decompile,
significant portions of Corel's Office for Java back into source code.
Decompilation is the process that transforms machine-readable code into
a human readable format. When an executable, a Java class file, or a DLL is
decompiled, you don't quite get the original format; instead you get a type of
pseudo source code, often incomplete and almost always without the comments.
But often what you get is more than enough to understand the original code.
The purpose of this book is to address an unmet need in the programming
community. For some reason, the ability to decompile Java has been largely
ignored even though it is relatively easy for anyone with the appropriate mindset
to do. In this book, I would like to redress the balance by looking at what tools
and tricks of the trade are currently being employed by people who are trying to
recover source code and those who are trying to protect it using, for example,
obfuscation.
This book is for those who want to learn Java by decompilation, those who sim-
ply want to learn how to decompile Java into source code, those who want to protect
their code, and finally those who want to better understand Java bytecodes and the
Java VIrtual Machine (JVM) by building a Java decompiler.
This book takes your understanding of decompilers and obfuscators to the
next level by

• Exploring Java bytecodes and opcodes in an approachable but detailed


manner.

• Using examples that show you what to do when an applet only partially
decompiles.

• Providing you with simple strategies you can use to show users how to
protect their code.

• Showing you what it takes to build your own decompiler.

1. Mocha was one of the early Java decompilers. You'll see more on Mocha later in this chapter.

1
Chapter 1

Compilers and Decompilers


Computer languages were developed because most normal people cannot work
in machine code or its nearest equivalent, Assembler. Thankfully, we realized
pretty early in computing technology that humans just weren't cut out to program
in machine code. Computer languages, such as Fortran, COBOL, C, Visual Basic,
and more recently, Java and C#, were developed to allow us to put our ideas in
a human-friendly format that can then be converted into a format that a computer
chip can understand.
At its most basic, the compiler's job is to translate this textual representation-
source code-into a series of O's and 1's-machine code-which the computer can
interpret as actions or steps that you want it to perform. It does this using a series
of pattern matching rules. A lexical analyzer tokenizes the source code2 and any
mistakes or words that are not in the compiler's lexicon are rejected immediately.
These tokens are then passed to the language parser, which matches one or more
tokens to a series of rules and translates these tokens into intermediate code
(some early versions ofVisual Basic, Pascal, and Java) or sometimes straight into
machine code (C and Fortran). Any source code that doesn't match a compiler's
rules is rejected and the compilation fails.
So now you know what a compiler does. Well, to be honest, you've only
scratched the surface; compiler technology has always been a specialized, and
sometimes complicated, area of computing. Modem advances mean things are
going to get even more complicated, especially in the virtual machine domain.
In part, this drive comes from Java and now .NET. Just in Time (JIT) compilers
have tried to close the gap between Java and C++ execution times by optimizing
the execution of Java bytecodes. This seems like an impossible task because
Java bytecode is, after all, interpreted, whereas C++ is compiled. But JIT com-
piler technology is making significant advances and is also making Java compilers
and virtual machines much more complicated beasts by incorporating these
advances.
From your point of view, you need to know that most compilers do a lot of
preprocessing and post-processing. The preprocessor readies the source code for
the lexical analysis by stripping out all unnecessary information, such as the
programmer's comments, and adding in any standard or included header files or
packages. A typical post-processor stage is coJe optimization, where the compiler
parses or scans the code, reorders it, and removes any redundancies, which will
hopefully increase the efficiency and speed of your code.
Decompilers, no big surprise here, translate the machine code or intermediate
code back into source code. In other words, the whole process is reversed. Machine
code is tokenized in some way and parsed or translated back into source code. This
transformation rarely results in original source code because some information is
lost in the pre- and post-processing stages.

2. Lexical comes from the word lexicon or dictionary.

2
Introduction

Take the analogy of idioms in human languages, which are often the most diffi-
cult part of a sentence or phrase to translate. My favorite idiom is Z:esprit d'escalier,
which literally translates as the wit ofthe staircase. But what it really means is that
perfect witty comment or comeback that pops into your head half an hour too late.
Similarly (and I know I'm stretching it a bit here) source code can often be translated
into machine code in more than one way. Java source code is designed for humans
and not computers, and often some steps may be redundant or can be performed
more quickly in a slightly different order. Because of these lost elements, few (if any)
decompilations result in the original source.

Virtual Machine Decompilers


Several notable attempts have been made to decompile machine code; Christina
Cifuentes' dec is one of the most recent. 3 However, at the machine code level, the
data and instructions are commingled, and it is a much more difficult, but not
impossible, to recover the original code.
In a virtual machine, the code has simply passed through a preprocessor and
the decompiler's job becomes one of simply reversing the preprocessing stages of
compilation. This makes interpreted code much, much easier to decompile. Sure,
there are no comments, and worse still, no specification, but then again, there are
also no research and development (R&D) costs.

Why Java?
The original ]VM was designed to run on a TV cable set-top box. As such, it was
a very small stack machine that pushed and popped its instructions on and off
a stack using only a limited instruction set. This made the instructions very easy
to understand with relatively little practice. Because the compilation process
was a two-stage process, the ]VM als,o required the compiler to pass on a lot of
information, such as variable and method names, that would not otherwise be
available. These names could be almost as helpful as comments when you were
trying to understand decompiled source code.
The current design of the JVM is independent of the Java 2 Software Development
Kit (SDK). In other words, the language and libraries may change, but the ]VM
and the opcodes are fixed. This means that if Java is prone to decompilation now,
then it is always likely to be prone to decompilation. In many cases, as you shall
see, decompiling a Java class is as easy as running a simple DOS or Unix command.

3. dec comes from cc, which used to be the standard command-line command for compiling
C programs, and still is, if like me you're IDE impaired.

3
Chapterl

In the future, the JVM may very well be changed to stop decompilation,
but this would break any backward compatibility and all current Java code
would have to be recompiled. And although this has happened before in the
Microsoft world with different versions ofVisual Basic, a lot more companies
than Sun develop virtual machines.
JVMs are now available for almost every operating system and web browser. In
fact, Java applets and applications can run on any computer or chip from a main-
frame right down to a handheld or a smartcard as long as a JVM and appropriate
class libraries exists for that platform. So it's no longer as simple as changing one
JVM,
What makes this situation even more interesting is that companies that want
to Java enable their operating system or browser usually create their own JVMs.
Sun is now only really responsible for the JVM specification. It seems that things
have now progressed so far that any fundamental changes to the JVM specification
would have to be backward compatible. Modifying the JVM to prevent decompila-
tion would require significant surgery, and in all probability, it would break this
backward compatibility, thus ensuring that Java classes will decompile for the fore-
seeable future.
It's true that no such compatibility restrictions exist on the Java SDK, where
more and more functionality is added almost daily. And the first crop of decom-
pilers did dramatically fail when inner classes were first introduced in the Java
Development Kit (JDK) 1.1. However, this isn't really a surprise because Mocha
was already a year out of date when 1.1 was released and other decompilers were
quickly modified to recognize inner classes.

Top Ten Reasons Why Java Is More


Vulnerable to Decompilation

1. For portability, Java code is partially compiled and then interpreted


bytheJVM.
2. Java's compiled classes contain a lot of symbolic information for the JVM,
3. Because of backward compatibility issues, the JVM's design is not likely
to change.
4. The JVM has very few instructions or opcodes.
5. The JVM is a simple stack machine.
6. Standard applets and applications have no real protection against
decompilation.
7. Java applets are typically small and therefore intelligible without com-
ments.

4
Introduction

8. Larger Java applications are automatically compiled into smaller modu-


lar classes.
9. Java applets are typically downloaded for free.
10. Java hype and cutthroat competition equal plenty of applications and
plenty of people willing to decompile them.

So unlike other Java books, I don't expect that this book will go out of date
with the next release of the JDK. Sure, some extra features may be added, but the
underlying architecture will remain the same. Let's begin with a simple example
in Listing 1-1.

Listing 1-1. Simple Java Source Code Example

public class Casting {


public static void main(String args[]){
for(char c=O; c < 128; C++) {
System.out.println("ascii " + (int)c + " character "+ c);
}
}
}

Listing 1-2 shows the output for a simple class file whose source is shown in
Listing 1-1 using javap, Sun's class file disassembler that came with the original
versions of Sun's JDK. You can decompile Java so easily because, as you'll see
later in the book, the NM is a simple stack machine with no registers and a lim-
ited number of high-level instructions or opcodes.

Listing 1-2. ]avap Output

Compiled from Casting.java


public synchronized class Casting extends java.lang.Object
I* ACC_SUPER bit set *I
{
public static void main(java.lang.String[]);
I* Stack=4, Locals=2, Args_size=l *I
public Casting();
I* Stack=l, Locals=l, Args_size=l *I
}

5
Chapter 1

Method void main(java.lang.String[])


o iconst_o
1 istore_1
2 goto 41
5 getstatic #12 <Field java.io.PrintStream out>
8 new #6 <Class java.lang.StringBuffer>
11 dup
12 ldc #2 <String "ascii ">
14 invokespecial #9 <Method java.lang.StringBuffer(java.lang.String)>
17 iload_1
18 invokevirtual #10 <Method java.lang.StringBuffer append(char)>
21 ldc #1 <String " character ">
23 invokevirtual #11 <Method java.lang.StringBuffer append(java.lang.String)>
26 iload_1
27 invokevirtual #10 <Method java.lang.StringBuffer append(char)>
30 invokevirtual #14 <Method java.lang.String toString()>
33 invokevirtual #13 <Method void println(java.lang.String)>
36 iload_1
37 iconst_1
38 iadd
39 i2c
40 istore_1
41 iload_1
42 sipush 128
4S if_icmplt 5
48 return

Method Casting()
o aload_o
1 invokespecial #8 <Method java.lang.Object()>
4 return<

It should be obvious that a lot of the source code information exists in


a class file; my aim is to show you how to take this information and reverse engi-
neer it into source code. However, in many cases, Java classes won't decompile
without some extra effort; you'll need to understand the underlying design and
architecture of a Java classfile and the JVM itself, which is what I'm going to pro-
vide you with in the remainder of this book.

History: Basic Chronology


Since before the dawn of the humble PC .... Scratch that. Since before the dawn
of COBOL, decompilers have been around in one form or another. In fact, you

6
Introduction

have to go all the way back to ALGOL to find the earliest example of a decom-
piler. Donnelly and Englanderwrote.D-Neliac at the Naval Electronic Labs (NEL)
in 1960. Its primary function was to convert non-Neliac compiled programs into
Neliac compatible binaries. Neliac was an ALGOL-type language that stood for
the Navy Electronics Laboratory International ALGOL Compiler.
Over the years, there have been other decompilers for COBOL, Ada, Fortran,
and many other esoteric as well as mainstream languages running on IBM main-
frames, PDP/Us, and Univacs, among others. Probably the main reason for these
early developments was to translate software or convert binaries to run on dif-
ferent hardware.
More recently, reverse engineering and the Y2K problem have become the
acceptable face of decompilation. Converting legacy code to get around the Y2K
problem often required disassembly or full decompilation. Reverse engineering
is a huge growth area that has not disappeared since the tum of the millennium.
Problems caused by the Dow Jones hitting the 10-thousand mark-ah, such fond
memories-and the introduction of the Euro have all caused financial programs
to fall over.
Even without these developments reverse engineering techniques are being
used to analyze old code, which typically has thousands of incremental changes,
in order to remove any redundancies and convert these legacy systems into much
more efficient animals.
At a much more basic level, hexadecimal dumps of PC machine code have
always given programmers extra insight into how something is achieved or into
how to break any artificial restrictions placed on the software. Magazine CDs
were either time-bombed or had restricted copies of games; these could be patched
to change demonstration copies into full versions of the software using primitive
disassemblers such as the DOS debug command.
Anyone well versed in Assembler can learn to quickly spot patterns in code
and bypass the appropriate source code fragments. Pirate software is a huge
problem for the software industry; disassembling the code is just one technique
employed by the professional or amateur bootlegger. Hence the downfall of many
an arcane copy protection technique.
However, the DOS debug command and Hexidecimal editors are primitive tools
and it would probably be quicker to write the code from scratch than to try to re-
create the source code from Assembler. For many years now, traditional software
companies have also been involved in reverse engineering software. They have
studied new techniques, and their competition has copied these techniques all
over the world using reverse engineering and decompilation tools. Generally, this
is accomplished using in-house decompilers, which are not for public consump-
tion and are definitely not going to be sold over the counter.
It's likely that the first real Java decompiler was actually written in IBM and
not by Hanpeter Van Vliet, author of Mocha. Daniel Ford's whitepaper Jive: A Java
Decompiler, dated May 1996, appears in IBM Research's search engines. This
whitepaper just beat Mocha, which wasn't announced until July 1996.

7
Chapter 1

Academic decompilers such as the University of Queensland's dec are avail-


able in the public domain. Fortunately for the likes of Microsoft, decompiling
Office using dec would create so much code that it would be about as user
friendly as Debug or a hexadecimal dump. Most modem commercial software's
source code is so large that it becomes unintelligible without the design docu-
ments and lots of source code comments. Let's face it; many people's C++ code
is hard enough to read six months after they wrote it. So how easy would it be
for someone else to decipher C code that came from compiled C++ code with-
out any help, even if the library calls aren't traversed?
What does come as a big surprise is the number of decompilers that are cur-
rently available but aren't that well publicized. Decompilers or disassemblers are
available for Clipper (Valkyrie), FoxPro (ReFox), Pascal, C (dec and decomp), Ada,
and, of course, Java. Even the Newton, loved by Doonesbury aficionados every-
where, isn't safe.
Not surprisingly, decompilers are much more common for interpreted lan-
guages, such as Visual Basic, Pascal, or Java, because of the larger amounts of
information being passed around. Some even have built-in dynamic compilers
that regenerate source code on the fly, which is then subsequently recompiled
into machine code, depending on the initial decompilation.

Visual Basic Decompilers


Let's take a look at Visual Basic (VB), another interpreted language, as an example
of what can happen to interpreted languages. Early versions ofVB were interpreted
by the vbrun. dll in a somewhat similar fashion to Java and the JVM; and just like
a Java classfile, the source code for VB programs is also bundled within the binary.
Bizarrely, Visual Basic 3 retains even more information than Java; this time even
the programmer's comments are included.
The original versions ofVB generated an intermediate pseudocode, called
p-code, which was also in Pascal and originates in the P-System. 4 And before you
say anything, yes, Pascal and all its derivatives are just as vulnerable; this state-
ment also includes early versions of Microsoft's C compiler, just so that nobody
else feels left out. The p-codes are not dissimilar to bytecodes and are essentially
VB opcodes that are interpreted by vbrun. dll at run time. Ever wonder why you
need to include vbrun. dll with VB executables? Well now you know-you need to
include vbrun. dll so that it can interpret the p-code and execute your program.
Doctor (Hans-Peter) Diettrich from Germany is the author of the epony-
mously titled DoDi-perhaps the most famous Visual Basic decompiler. These
days DoDi-also known as Vbis3-is outdated because it only decompiles VB3
binaries, although there were rumors of a version for VB4. But because VB

4. http://www.threedee.com/jcm/psystem/

8
Introduction

moved to compiled rather than interpreted code, the number of decompilers


completely fell away.
At one time, Visual Basic also had its own culture of decompilers and obfus-
cators, or protection tools as they're called in VB. Doctor Diettrich provides
VBGuard for free on his site, and other programs, such as Decompiler Defeater,
Protect, Overwrite, Shield, and VBShield, are available from other sources. But
they too have all but disappeared with VB5 and VB6.
This was, of course, before .NET. With the arrival of .NET, we've once again
come full circle and VB is once again interpreted. Not surprisingly, we're already
seeing decompilers and obfuscators such as the Exemplar andAnakrino decom-
pilers as well as Demeanor and Dotfuscator.

Hanpeter Van Vliet

Oddly enough for a technical subject, this book also has a very human element.
HanpeterVan Vliet wrote the first public domain decompiler, Mocha, while recov-
ering from a cancer operation in the Netherlands. He also wrote an obfuscator
called Crema that attempted to protect an applet's source code. If Mocha was the
Uzi machine gun, then Crema was the bulletproof jacket. In a now classic Internet
marketing strategy, Mocha was free, whereas there was a small charge for Crema.
The beta version of Mocha caused a huge controversy when it was first made
available on Hanpeter's web site, especially after it was featured in a clnet article.
Because of the controversy, Hanpeter took the very honorable step of removing
Mocha from his web site. He then held a vote about whether or not Mocha should
once again be made available. The vote was ten to one in favor of Mocha, and
soon after it reappeared on Hanpeter's web site.
However, Mocha never made it out of beta, and while I was conducting some
research for a Web Techniques article on this very subject, I learned from his wife
that Hanpeter's throat cancer finally got him. He died at the age of 34 on New
Year's Eve, 1996.
The source code for both Crema and Mocha were sold to Borland shortly
before Hanpeter's death, with all proceeds going to Hanpeter's wife, Ingrid. Some
early versions of ]Builder shipped with an obfuscator, which was probably Crema
This attempted to protect Java code from decompilation by replacing ASCII variable
names with control characters.
I'll talk more about the host of other Java decompilers and obfuscators later
in the book.

Legal Issues
Before you start building your own decompiler, why don't you take this opportunity
to consider the legal implications of decompiling someone else's code for your own
enjoyment or benefit? Just because Java has taken decompiling technology out of

9
Chapter 1

some very serious propeller head territory and into more mainstream computing
doesn't make it any less likely that you or your company will get sued. It may make
it more fun, but you really should be careful.
To start with, why don't you try following this small set of ground rules:

• Do not decompile an applet, recompile it, and then pass it off as your own.

• Don't even think of trying to sell a recompiled applet to any third parties.

• Try not to decompile an applet or application that comes with a license


agreement that expressly forbids decompiling or reverse engineering
the code.

• Don't decompile an applet to remove any protection mechanisms and


then recompile it for your own personal use.

Over the past few years, big business has tilted the law firmly in its favor
when it comes to decompiling software. Companies can use a number of legal
mechanisms to stop you from decompiling their software; these would leave you
with little or no legal defense if you ever had to appear in a court oflaw if some-
one discovered that you had decompiled their programs. Patent law, copyright
law, anti-reverse engineering clauses in shrink.wrap licenses, as well as a number
of laws such as the Digital Millennium Copyright Act (DMCA) may all be used
against you. Different laws may apply in different countries or states; for exam-
ple, the "no reverse engineering clause" software license is a null and void clause
in the European Union (EU), but the basic concepts are the same-decompile
a program for the purpose of cloning the code into another competitive product
and you're probably breaking the law.
The secret here is that you shouldn't be standing, kneeling, or pressing down
very hard on the legitimate rights-that is, the copyright rights-of the original
author. That's not to say that conditions exist in which it is OK to decompile.
However, certain limited conditions do exist where the law actually favors decom-
pilation or reverse engineering through a concept known as fair use. From almost
the dawning of time, and certainly from the beginning of the industrial age, many
of humankind's greatest inventions have come from an individual who has created
something special while standing on the shoulders of giants. For example, both the
invention of the steam train and the common light bulb were relatively modest
incremental steps in technology. The underlying concepts were provided by other
people, and it was up to Stephenson or Edison to create the final object. You can
see an excellent example of the Stephenson's debt to many other inventors such as
James Watt in the following timeline of the invention of the Stephenson's Rocket at
http: I !Wt~N. usgennet. org/usa/topic/steam/timeline. html. This concept ofstanding
on the shoulders of giants is one of the reasons why patents first appeared-to
allow people to build on other creations while still giving the original inventor
some compensation for their initial idea for period of, say, 20 years.
10
Introduction

In the software arena, trade secrets are typically protected by copyright law
rather than through any patents. Sure, patents can protect certain elements of
a program, but it is highly unlikely that a complete program will be protected by
a patent or a series of patents. Software companies want to protect their invest-
ment, so they typically turn to copyright law or software licenses to prevent
people from essentially stealing their research and development efforts.
Copyright law is not rock solid; if it was, there would be no inducement to
patent an idea and the patent office would quickly go out of business. Copyright
protection does not extend to interfaces of computer programs, and a developer
can use the fair use defense if they can prove that they decompiled the program
to see how they could intemperate with any unpublished application program-
ming interfaces (APis) in the program.
If you are living in the EU, then more than likely you work under the EU
Directive on Legal Protection of Computer Programs. This states that you can
decompile programs under certain restrictive circumstances-for example,
when you are trying to understand the functional requirements you need to
create a compatible interface to your own program. Or, to put it another way,
if you need access to the internal calls of a third party program and the authors
refuse to divulge the APis at any price. Then, under the EU directive, you could
decompile the code to discover the APis. However, you'd have to make sure that
you were only going to use this information to create an interface to your own
program rather than create a competitive product. You also cannot reverse
engineer any areas that have been protected in any way.
For many years Microsoft's applications have allegedly gained unfair advan-
tage from underlying unpublished APis calls to Wmdows 3.1 and Wmdows 95
that are orders of magnitude quicker than the published APis. The Electronic
Frontier Foundation (EFF) has come up with a useful road map analogy to help
explain this. Say you are trying to travel from Detroit to New York, but your map
doesn't show any interstate routes. Sure, you'd eventually get there traveling on
the back roads, but the trip would be a lot shorter if you had the Microsoft map,
complete with interstates. If these conditions were true, the EU directive would
be grounds for disassemblingWmdows 2000 or Microsoft Office (MSOffice), but
you better hire a good lawyer before you try it. Personally, I don't buy it as I can't
believe MSOffice could possibly be any slower than it currently is, so if there are
any hidden APis, they certainly don't seem to be causing any impact on the
speed of any of the MSOffice applications.
There are precedents that allow legal decompilation in the US too. The most
famous case to date is Sega v. Accolade. 5 In 1992, Accolade won a case against
Sega that ruled that their unauthorized disassembly of the Sega object code was
not copyright infringement. Accolade reverse engineered Sega's binaries into an
intermediate code that allowed them to extract a software key. This key allowed
Accolade's games to interact with Sega Genesis video consoles. Obviously Sega

5. http://www.eff.org/Legal/Cases/sega_v_accolade_977f2d1510_decision.html

11
Chapter 1

was not going to give Accolade access to APis, or in this case, code, to unlock the
Sega game platform. The court ruled in favor of Accolade judging that the
reverse engineering constituted fair-use. But before you think this gives you
carte blanche to decompile code, you might like to know that Atari v. Nintendo6
went against Atari under very similar circumstances.
In conclusion-see you can tell this is the legal section-the court cases in the
US and the EU directive stress that under certain circumstances reverse engineer-
ing can be used to understand the interoperability and create a program interface.
It cannot be used to create a copy to sell as a competitive product. Most Java
decompilation will not fall into this interoperability category. It is far more likely
that the decompiler wants to pirate the code, or at best, understand the underlying
ideas and techniques behind the software.
It is not very clear if reverse engineering to discover how an applet was written
would constitute fair use. The US Copyright Act of 1976's exclusion of "any idea,
procedure, process, system, method of operation, concept, principle or discovery,
regardless of the form in which it is described" makes it sound like the beginning
of a defense for decompilation, and fear of the fair use clause is one of the reasons
why more and more software patents are being issued. Decompilation to pirate or
illegally sell the software cannot be defended.
However, from a developer's point of view, the situation looks bleak. The only
protection-in the form of a user's license-is about as useful as the laws against
copying music CDs or audiocassettes. It won't physically stop anyone from mak-
ing illegal copies and it doesn't act as any real deterrent for the home user. No
legal recourse will protect your code from a hacker, and it sometimes seems that
the people trying to create many of today's secure systems must feel like they are
standing on the shoulders of morons. You only have to look at the recent investi-
gation into eBook protection schemes7 and the whole DeCSS fiasco 8 to see how
paper-thin a lot of the recent so called secure systems really are.

Moral Issues
Decompiling Java is an excellent way to learning both the Java language and how
the NM works. It helps people climb up the Java learning curve because they
learn by seeing other people's programming techniques. The ability to decompile
applets or applications can make the difference between a basic understanding of
Java and an in-depth knowledge. Learning by example is one of the most power-
ful tools. It helps even more if you can pick your own examples and modify them
to your own needs.

6. http://cyber.law.harvard.edu/openlaw/DVD/cases/atarivnintendo.html
7. http://slashdot.org/article.pl?sid=01/07/17/130226
8. http://cyber.law.harvard.edu/openlaw/DVD/resources.html

12
Introduction

However, my book on decompiling would not be complete if I didn't discuss


the morality issues behind what amounts to stealing someone else's code. In the
early days of software, it was not uncommon to receive the source code with the
product. But in the last few decades, market economics have taken over and this
practice has almost disappeared with some notable open source exceptions such
as GNU and Linux. But now, due to a certain set of circumstances, we find that
Java comes complete with its source code.
The author, the publisher, the author's agent, and his agent's mother would
like to state that we are not advocating that readers of this book decompile pro-
grams for anything other than educational purposes. The purpose of this book is to
show readers how to decompile source code, but we are not encouraging anyone
to decompile other programmers' code and then try to use it, sell it, or repackage it
as if it was their own. Please be careful that you do not try to reverse engineer any
code that has a licensing agreement stating that you should not decompile it. It is
not fair, and you'll only get yourself in trouble. Having said that, there are thou-
sands of applets on the Web, which when decompiled, will help you understand
good and bad Java programming techniques.
To a certain extent, I'm pleading the "Don't shoot the messenger" defense.
I'm not the first to spot this flaw in Java, and I certainly won't be the last person
to write about the subject. My reasons for writing this book are, like the early
days of the Internet, fundamentally altruistic. Or, in other words, I found this
cool trick and I want to tell everyone about it.
Having said this, let me remind you that you can never be sure that the decom-
piler generated code that was 100 percent accurate. So you're in for a nasty surprise
if you intend to use Java decompilation as the basis for your own products.

Protecting Yourself
Pirated software is a big headache for many software companies and big business
for others. At the very least, software pirates could use decompilers to remove any
licensing restrictions, but imagine the consequences if the technology was available
to decompile Office 2000, recompile it, and sell it as a new competitive product. To
a certain extent, that could easily have happened when Corel released the beta ver-
sion of Corel's Office for Java.
Perhaps this realization is starting to dawn on Java software houses. We are
beginning to see two price scales on Java components: one for the classes and
one for the source code. This is entirely speculative, but it seems that companies
such as Sitraka (now Quest) realized that a certain percentage of their users
would decompile their classes, and as a result, a few years ago Sitraka chose to
sell the source code for JClass as well as other components. This makes any
decompilation redundant as the code is provided along with the classes and it
also makes some money for the developer by charging a little extra for the
source code.

13
Chapter 1

But is all doom and gloom? Should you just resign yourselves to the fact that
Java code can be decompiled or is there anything you can do to protect your code?
Here are some options:

• License agreements

• Protection schemes within your code

• Code fingerprinting

• Obfuscation

• Intellectual Property Rights UPR) protection schemes

• Executable applications

• Server-side code

• Encryption

Although you'll look at all these in more detail later, you should know that
the first four only act as deterrents and the last four are effective, but have other
implications. Let me explain.
license agreements don't offer any real protection from a programmer who
wants to decompile your code.
Spreading protection schemes throughout your code, such as by using combi-
nations of getCodeBase and getDocumentBase or server authentication, is useless
because they can be simply commented out of the decompiled code.
Code fingerprinting is what happens when spurious code is used to watermark
or fingerprint source code, and it can be used in conjunction with license agree-
ments, but it is only really useful in a court of law. Better decompilation tools will
profile the code and remove any extra dummy code.
Obfuscation replaces the method names and variable names in a class file
with weird and wonderful names. This is an excellent deterrent, but the source
code is still visible and in conjunction with obfuscated code when the better
decompilers are used, so often this is not much better than compiling without
the debug flag. HoseMocha, another obfuscator, works by adding a spurious
pop bytecode after every return; it does nothing to the code but it does kill the
decompiler. However, developers can quickly modify their decompiler once
this becomes apparent, assuming they're still around to make the changes.
IPR protection schemes such as IBM's Cryptolope Live!, InterTrust's DigiBox,
and Breaker Technologies' SoftSEAL are normally used to sell HTML documents
or audio files on some pay-per-view basis or pay-per-group scheme. However,
because they typically have built in trusted HTML viewers, they allow Java applets
to be seen but not copied. Unfortunately IPR protection schemes are not cheap.
14
Introduction

Worse still, some of the clients are written in 100 percent pure Java and can
therefore be decompiled.
The safest protection for Java applications is to compile them into executables.
This is an option on many Java compilers-SuperCede, for example. Your code will
now be as safe as any C or C++ executables-read a lot safer-but it will no longer
be portable because it no longer uses the NM.
The safest protection for applets is to hide all the interesting code on the
web server and only use the applet as a thin, front-end graphical user interface
(GUI). This has a downside; it may increase your web server load to unaccept-
able levels.
Several attempts have been made to encrypt a classfile's content and then
decrypt it in the classloader. Although at first glance this seems like an excellent
approach, sooner or later the classfile's bytecode has to be decrypted in order to
be executed by the NM, at which point it can be intercepted and decompiled.

Book Outline
Decompiling Java is not a normal Java language book. In fact, it is the complete
opposite of a standard Java textbook where the author teaches you how to trans-
late ideas and concepts into Java. You're interested in turning the partially compiled
Java bytecodes back into source code so that you can see what the original pro-
grammer was thinking. I won't be covering the language structure in depth, except
where it relates to bytecodes and the NM. All emphasis will be on Java's low-level
design rather than on the language syntax.
In the first part of this book, Chapters 2 through 4, I'll unravel the Java classfile
format and show you how your Java code is stored as bytecode and subsequently
executed by the NM. You'll also look at the theory and practice of decompilation
and obfuscation. I'll present some of the decompiler's tricks of the trade and explain
how to unravel the Java bytecode of even the most awkward class. You'll look at the
different ways people try to protect the source code and, when appropriate, learn to
expose any flaws or underlying problems with the different techniques so that you'll
be suitably informed before you purchase any source code protection tools.
The second part of this book, Chapters 5 and 6, I will primarily focus on how
to write your own Java decompiler. You'll build an extendable Java bytecode
decompiler. You'll do this for two reasons. First, although the NM design is fixed,
the language is not. Many of the early decompilers cannot handle Java con-
structs that appeared in the JDK 1.1, such as inner classes. Second, one of my
own personal pet peeves is reading a technical computer book that stops when
things are just getting interesting. The really difficult problems are then left to
the reader as an exercise. For some unknown reason, this seems to be particu-
larly true of Internet-related books. Partly as a reaction against that mentality,
I'm going to go into decompilers in some detail with plenty of practical examples
in hopefully as approachable a manner as possible.

15
Chapter 1

And while we're on the subject of pet peeves-sorry, I'll try to keep them to
a minimum-I won't be covering a potted history of the Internet or indeed Java.
This has been covered too many times before. If you want to know about the
ARPANET and Oak, then I'm afraid you're going to have to look elsewhere.9

Conclusion
Java decompilation is one of the best learning tools for new Java programmers.
What better way to find out how to write code than by taking an example off the
Internet and decompiling it into source code? It's also a necessary tool when
some dotcom web developers have gone belly up and the only way to fix their
code is to decompile it yourself. But it's also a menace if you're trying to protect
the investment of countless hours of design and development.
The aim of this book is to create some dialog about decompilation and
source code protection. I also want to separate the fact from fiction and show
you how easy it is to decompile code and what measures you can take to protect
it. Both Sun and Microsoft will tell you that decompilation isn't an issue and that
a developer can always be trained to read a competitor's Assembler, but separate
the data from the instructions and this task becomes orders of magnitude easier.
Don't believe it? Then read on and decide for yourself.

9. Such as Core Java 2, 6th edition, by CayS. Horstmann and Gary Cornell (Prentice Hall PTR,
2002).

16
CHAPTER 2

Ghost 1n

the Machine
IF You'RE TRYING to understand just how good an obfuscator or decompiler really
is, then it helps to be able to see what's going on inside a classfile. Otherwise you're
relying on the word of a third-party vendor or, at best, a knowledgeable reviewer.
For most people, that's not good enough when you're trying to protect mission
critical code. At the very least, you should be able to talk intelligently about the
area and ask the obvious questions to understand just what's happening.

Pay no attention to the man behind the curtain.


-Wizard ofOz

At this moment, all sorts of noises are coming out of Microsoft in Redmond
saying that there really isn't anything to worry about when it comes to decompil-
ing .NET code. Sure, hasn't everyone been doing it for years at the Assembly level?
Similar noises were made when Java was in its infancy.
So, in this chapter, you'll be pulling apart a Java classfile to lay the founda-
tion for the following chapters on obfuscation theory and to help you during
the design of your decompiler. In order to get to that stage, you need to under-
stand bytecodes, opcodes, classfiles, and how they relate to the Java Virtual
Machine (JVM).
Several very good books are on the market about the JVM. The best is Bill
Verner's Inside the Java Virtual Machine (McGraw-Hill, 1998). Some of the
book's chapters are available online at http://www.artima.com/insidejvm/ed2/.
If you can't find this book, then check out Verner's equally excellent "Under
the Hood" articles inJavaWorld. This series of articles was the original mater-
ial on which the book was based. Sun's Java Virtual Machine Specification
(2nd Edition), written by Tim Lindholm and Frank Yellin, is both comprehen-
sive and very informative for would-be decompiler writers. But because it is
a specification, it is not what you would call a good read. This book is available
online at http: I /java. sun. com/docs/books/vmspec or you can purchase it
(Addison-Wesley, 1999).
Oddly enough, I've yet to see a book that covers how to build a JVM; every
book published so far focuses on the abstract JVM rather than how someone
would implement one. With the rise of alternative JVMs from IBM and others,
I really expected to see at least one JVM book full of C code for converting byte-
code to executable native code, but it never came. Perhaps this is because it

17
Chapter2

would have a very limited audience and its sales would be in the hundreds rather
than the thousands.
However, my focus is very different from other JVM books. You could say I'm
approaching things from the completely opposite direction. Your task is to get
from bytecode to source, whereas everyone else wants to know how source is
translated into bytecode and ultimately executed. You should be much more
interested in how a classfile can be turned into source rather than how a classfile
is interpreted.
In this chapter, you'll be looking at how a classfile can be disassembled into
bytecodes and how these bytecodes can be turned into source. Of course, you
need to know how each bytecode functions, but you should be less interested in
what happens to them when they are within the ]VM, and my emphasis will dif-
fer accordingly.

The JVM: An Exploitable Design?


Java classfiles are designed to be quickly transmitted across a network or via the
Internet. As a result, they are compact and are relatively simple to understand.
For portability, a classfile is only partially compiled into bytecodes by javac, Sun's
Java compiler. This is then interpreted and executed by a JVM, usually on a com-
pletely different machine or operating system.
The JVM's classfile interface is strictly defined by Sun's Java Virtual Machine
Specification. But how a JVM ultimately turns bytecodes into machine code is
left up to the developer. However, that really shouldn't concern you, because
once again, your interest should stop at the JVM. It may help if you think of
classfiles as being analogous to object files in other languages, such as C or C++,
waiting to be linked and executed by the JVM only with a lot more symbolic
information.
There are many good reasons why a classfile carries around so much infor-
mation. For many, the Internet is seen as a bit of a modern day Wild West where
crooks and criminals are plotting to infect your hard disk with a virus or waiting
to grab any credit card details that might pass their way. As a result, the JVM was
designed from the bottom up to protect web browsers from any rogue applets.
Through a series of checks, the JVM and the class loader make sure that no mali-
cious code can be uploaded onto a web page.
However, all checks have to be performed lightning-quick to cut down on the
download time, so it's not really surprising that the original JVM designers opted
for a simple stack machine with lots of information available for those crucial
security checks. In fact, the design of the JVM is pretty secure even though some
of the early browser implementations made a couple or three serious blunders.
Unfortunately for developers, what keeps the code secure also makes it much
easier to decompile. The JVM's restricted execution environment and uncomplicated

18
Ghost in the Machine

architecture, as well as the high-level nature of many ofits instructions, all conspire
against the programmer in favor of the decompiler.
At this point, it is probably also worth mentioning the fragile superclass prob-
lem. When a new method is added in C++, all classes that reference that class need
to be recompiled. Java gets around this by putting all the necessary symbolic infor-
mation into the classfile. The NM then takes care of all the linking and final name
resolution, loading all the required classes-including any externally referenced
fields and methods-on the fly. This delayed linking or dynamic loading, possibly
more than anything else, is why Java is so much more prone to decompilation.
By the way, I'm going to ignore native methods in these discussions. Native
methods, of course, are when some native C or C++ code is incorporated into the
application. This spoils Java application portability, and is one surefire way to
prevent a Java program from being decompiled.
So without further ado, let's take a brief look at the design of the NM.

Simple Stack Machine


The NM is in essence a simple stack machine with a program register to take
care of the program flow thrown in for good luck. The Java class loader takes the
class and presents it to the NM.
You can split the NM into four separate but distinct parts.

• Heap

• Program counter registers

• Method area

• Stack

Every application or applet has its own heap and method area and every thread
has its own register or program counter and program stack. Each program stack is
then further subdivided into stack frames, with each method having its own stack
frame. That's a lot of information for one paragraph, so in Figure 2-1, I illustrate this
in a simple diagram.

19
Other documents randomly have
different content
No doubt, Caleb profoundly agreed with this characterisation of
Letizia, held he up never so plump a protestant hand.
“Oh, do give your consent to our marriage,” he gurgled. “I know
that there is a difference of religion. But I have ventured to think once
or twice that you could overlook that difference. I have remarked
sometimes that you did not appear to attach very great importance to
your religion. I’ve even ventured to pray that you might come in time
to perceive the errors of Romanism. In fact, I have dreamed more
than once, ma’am, that you were washed in the blood of the Lamb.
However, do not imagine that I should try to influence Letizia to
become one of the Peculiar Children of God. I love her too dearly,
ma’am, to attempt any persuasion. From a business point of view—
and, after all, in these industrious times it is the business point of
view which is really important—from a business point of view the
match would not be a very bad one. I have a few humble savings,
the fruit of my long association with you in your enterprises.”
Caleb paused a moment and took a deep breath. He had reached
the critical point in his temptation of Madame Oriano, and he tried to
put into his tone the portentousness that his announcement seemed
to justify.
“Nor have I been idle in my spare time, ma’am. No, I have devoted
much of that spare time to study. I have been rewarded, ma’am. God
has been very good to me and blessed the humble talent with which
he entrusted me. Yes, ma’am. I have discovered a method of using
chlorate of potash in combination with various other chemicals which
will undoubtedly revolutionise the whole art of pyrotechny. Will you
consider me presumptuous, ma’am, when I tell you that I dream of
the moment when Fuller’s Fireworks shall become a byword all over
Great Britain for all that is best and brightest in the world of
pyrotechny?”
Madame Oriano’s eyes flashed like Chinese fire, and Caleb,
perceiving that he had made a false move, tried to retrieve his
position.
“Pray do not suppose that I was planning to set myself up as a
manufacturer of fireworks on my own. So long as you will have me,
ma’am, I shall continue to work for you, and if you consent to my
marrying your Letizia I shall put my new discovery at your service on
a business arrangement that will satisfy both parties.”
Madame Oriano pondered the proposal in silence for a minute.
“Yes, you can have Letizia,” she said at last.
Caleb picked up the hand that was hanging listlessly over the
coverlet and in the effusion of his gratitude saluted it with an oily
kiss.
“And you’ll do your best to make Letizia accept me as a husband?”
he pressed.
“If I say you can have Letizia, caro, you willa have her,” the mother
declared.
“You have made me the happiest man in England,” Caleb oozed.
Whereupon he walked on tiptoe from the room with a sense even
sharper than usual that he was one of the Lord’s chosen vessels, a
most peculiar child even among the Peculiar Children of God.
Just when the hot August day had hung two dusky sapphire lamps
in the window of the room, Madame Oriano, who had been lying all
the afternoon staring up at the shadows of the birds that flitted
across the ceiling, rang the bell and demanded her daughter’s
presence.
“Letizia, devi sposarti,” she said firmly.
“Get married, mamma? But I don’t want to be married for a long
time.”
“Non ci entra, cara. Devi sposarti. Sarebbe meglio—molto meglio.
Sei troppo sfrenata.”[7]

[7] “That doesn’t come into it, my dear. You must get
married. It would be better—much better. You are too
harum-scarum.”
“I don’t see why it should be so much better. I’m not so harum-
scarum as all that. Besides, you never married at my age. You never
married at all if it comes to that.”
“Lo so. Perciò dico che tu devi sposarti.”[8]

[8] “I know that. That’s why I say that you must get married.”

“Thanks, and who am I to marry?”


“Caleb.”
“Caleb? Gemini! Caleb? Marry Caleb? But he’s so ugly! And he
don’t wash himself too often, what’s more.”
“Bello non é ... ma che importa? La bellezza passa via.”
“Yes, I daresay beauty does pass away,” said Letizia indignantly.
“But it had passed away from Caleb before ever he was born.”
“Che importa?”
“I daresay it don’t matter to you. But you aren’t being expected to
marry him. Besides, you’ve had all the beaux you wanted. But I
haven’t, and I won’t be fobbed off with Caleb. I just won’t be, and you
may do what you will about it.”
“Basta!” Madame Oriano exclaimed. “Dissa talk is enough.”
“Basta yourself and be damned, mamma,” Letizia retorted. “I won’t
marry Caleb. I’d sooner be kept by a handsome gentleman in a big
clean cravat. I’d sooner live in a pretty house he’d give me and drive
a crimson curricle on the Brighton Road like Cora Delaney.”
“It does not import two pennies what you wish, figlia mia. You willa
marry Caleb.”
“But I’m not in love with him, the ugly clown!”
“Love!” scoffed her mother. “L’amore! L’amore! Love is mad. I have
hadda so many lovers. Tanti tanti amanti! Adesso, sono felice? No!
Ma sono vecchia assai. Yes, an old woman—una vecchia miserabile
senza amanti, senza gambe—e non si fa l’amore senza gambe,
cara, ti giuro—senza danaro, senza niente.”
Sans love, sans legs, sans money, sans everything, the old
woman dropped back on her pillows utterly exhausted. A maid came
in with candles and pulled the curtains to shut out the dim grey into
which the August twilight had by now gradually faded. When the
maid was gone, she turned her glittering, sombre eyes upon her
daughter.
“You willa marry Caleb,” she repeated. “It willa be better so—molto
meglio cosi. Gli amanti non valgono niente. All who I have been
loving, where are dey now? Dove sono? Sono andati via. Alla gone
away. Alla gone. You willa marry Caleb.”
Letizia burst into loud sobs.
“But I don’t want to marry, mamma.”
“Meglio piangere a diciasette che rimpiangere a sessanta,”[9] said
Madame Oriano solemnly. “You willa marry Caleb.”

[9] “Better to weep at seventeen than to repine at sixty.”

Letizia felt incapable of resisting this ruthless old woman any


longer. She buried her head in the gaudy satin coverlet and wept in
silence.
“Allora dammi un bacio.”
The obedient daughter leaned over and kissed her mother’s lined
forehead.
“Tu hai già troppo l’aria di putana, figlia mia. Meglio sposarti.
Lasciammi sola. Vorrei dormire. Sono stanca assai ... assai.”[10]

[10] “You have already too much the air of a wanton, my


daughter. Better to get married. Leave me alone. I want to
sleep. I’m very tired.”
Madame Oriano closed her eyes, and Letizia humbly and
miserably left her mother, as she wished to be left, alone.
CHAPTER IV
MARRIED LIFE
So, Caleb Fuller married Letizia Oriano and tamed her body, as
without doubt he would have succeeded in taming the body of any
woman of whom he had lawfully gained possession.
Madame Oriano did not long survive the marriage. The effort she
made in imposing her will upon her daughter was too much for a
frame so greatly weakened. Once she had had her way, the desire to
live slowly evaporated. Yet she was granted a last pleasure from this
world before she forsook it for ever. This was the satisfaction of
beholding with her own eyes that her son-in-law’s discovery of the
value of chlorate of potash as a colour intensifier was all that he
claimed for it. That it was likely to prove excessively dangerous when
mixed with sulphur compounds did not concern this pyrotechnist of
the old school. The prodigious depth and brilliant clarity of those new
colours would be well worth the sacrifice of a few lives through
spontaneous ignition in the course of manufacturing them.
The first public demonstration that Caleb gave was on the evening
of the Fifth of November in a Clerkenwell tea-garden. It is unlikely
that Madame Oriano ever fully comprehended the significance of
these annual celebrations. If she ever did wonder who Guy Fawkes
was, she probably supposed him to be some local English saint
whose martyrdom deserved to be commemorated by an abundance
of rockets. As for Caleb, he justified to himself some of the pleasure
that his fireworks gave to so many people by the fact that the chief
festival at which they were employed was held in detestation of a
Papist conspirator.
On this particular Fifth of November the legless old lady was
carried in an invalid’s chair through the press of spectators to a
favourable spot from which she could judge the worth of the
improved fireworks. A few of the rabble jumped to the conclusion
that she was a representation of Guy Fawkes himself, and set up the
ancient chorus:

Please to remember the Fifth of November


Gunpowder treason and plot;
We know no reason why gunpowder treason
Should ever be forgot!
A stick and a stake for King George’s sake,
A stick and a stump for Guy Fawkes’s rump
Holla, boys! holla, boys! huzza-a-a!

Madame Oriano smiled grimly when Caleb tried to quiet the


clamour by explaining that she was flesh and blood.
“Letta dem sing, Caleb. Non fa niente a me. It don’ta matter
notting to me.”
A maroon burst to mark the opening of the performance. This was
followed by half-a-dozen rockets, the stars of which glowed with
such greens and blues and reds as Madame Oriano had never
dreamed of. She tried to raise herself in her chair.
“Bravo, Caleb! Bravissimo! Ah dio, non posso più! It is the besta
colore I havva ever seen, Caleb. E ottimo! Ottimo, figlio mio.”
She sat entranced for the rest of the display; that night, like a
spent firework, the flame of her ardent life burnt itself out.
The death of his mother-in-law allowed Caleb to carry out a plan
he had been contemplating for some time. This was to open a
factory in Cheshire on the outskirts of his native town. He anticipated
trouble at first with the Peculiar Children of God, who were unlikely to
view with any favour the business of making fireworks. He hoped,
however, that the evidence of his growing prosperity would presently
change their point of view. There was no reason to accuse Caleb of
hypocrisy, or to suppose that he was anything but perfectly sincere in
his desire to occupy a high place in the esteem of his fellow
believers. Marriage with a Papist had in truth begun to worry his
conscience more than a little. So long as Letizia had been a
temptation, the fact of her being a daughter of Babylon instead of a
Peculiar Child of God had only made the temptation more
redoubtable, and the satisfaction of overcoming it more sharp. Now
that he was licensed to enjoy her, he began to wonder what effect
marriage with a Papist would have on his celestial patron. He felt like
a promising young clerk who has imperilled his prospects by
marrying against his employer’s advice. It began to seem essential
to his salvation that he should take a prominent part in the prayer-
meetings of the Peculiar Children of God. He was ambitious to be
regarded himself as the most peculiar child of all those Peculiar
Children. Moreover, from a practical standpoint the opening of a
factory in the North should be extremely profitable. He already had
the London clients of Madame Oriano; he must now build up a solid
business in the provinces. Fuller’s Fireworks must become a byword.
The King was rumoured to be ill. He would be succeeded by another
king. That king would in due course have to be solemnly crowned.
Liverpool, Manchester, Sheffield, Leeds, and many other large towns
would be wanting to celebrate that coronation with displays of
fireworks. When the moment arrived, there must be nobody who
would be able to compete with Fuller and his chlorate of potash.
So to Brigham in Cheshire Caleb Fuller brought his wife. In some
fields on the outskirts of the town in which he had spent a poverty-
stricken youth he built his first sheds, and in a dreary little street
close to Bethesda, the meeting-house of the Peculiar Children of
God, he set up his patriarchal tent. Here on a dusty September dawn
just over two years after her last public appearance at “Neptune’s
Grotto,” Letizia’s eldest daughter was born. The young wife of Caleb
was not yet thoroughly tamed, for she produced a daughter exactly
like herself and called her Caterina in spite of the father’s objection
to a name associated with the wheels of which he made so many.
Not only did she insist on calling the child Caterina, but she actually
took it to the nearest Catholic chapel and had it baptised by a priest.
It happened about this time that one of the apostles of the
meeting-house was gravely ill, and Caleb, who had designs on the
vacant apostolic chair, decided that his election to it must not be
endangered by the profane behaviour of his young wife. When he
remonstrated with her, she flashed her eyes and tossed her head as
if he were still Caleb the clerk and she the spoilt daughter of his
employer.
“Letizia,” he said lugubriously, “you have destroyed the soul of our
infant.”
“Nonsense!”
“You have produced a child of wrath.”
“My eye!” she scoffed.
Caleb’s moist lips vanished from sight. There was a long silence
while he regarded his wife with what seemed like two pebbles of
granite. When at last he spoke, it was with an intolerable softness.
“Letizia, you must learn to have responsibilities. I am frightened for
you, my wife. You must learn. I do not blame you entirely. You have
had a loose upbringing. But you must learn.”
Then, as gently as he was speaking, he stole to the door and left
Letizia locked behind him in her bedroom. Oh, yes, he tamed her
body gradually, and for a long time it looked as if he would tame her
soul. She had no more daughters like herself, and each year for
many years she flashed her eyes less fiercely and tossed her head
less defiantly. She produced several other children, but they all took
after their father. Dark-eyed Caterina was followed by stodgy
Achsah. Stodgy Achsah was followed by podgy Thyrza. These were
followed by two more who died almost as soon as they were born, as
if in dying thus they expressed the listlessness of their mother for this
life. Maybe Letizia herself would have achieved death, had not the
way Caleb treated little Caterina kept her alive to protect the child
against his severity.
“Her rebellious spirit must be broken,” he declared, raising once
more the cane.
“You shall not beat her like this, Caleb.”
“Apostle Jenkins beat his son till the child was senseless, because
he stole a piece of bread and jam.”
“I wish I could be as religious as you, Caleb,” said his wife.
He tried to look modest under the compliment.
“Yes,” she went on fiercely, “for then I’d believe in Hell, and if I
believed in Hell I’d sizzle there with joy just for the pleasure of seeing
you and all your cursed apostles sizzling beside me.”
But Letizia did not often break out like this. Each year she became
more silent, taking refuge from her surroundings in French novels
which she bought out of the meagre allowance for clothes that her
husband allowed her. She read French novels because she
despised the more sentimental novelists of England that were so
much in vogue at this date, making only an exception in favour of
Thackeray, whom she read word for word as his books appeared.
She was learning a bitter wisdom from literature in the shadows and
the silence of her wounded heart. After eight years of married life she
bore a son, who was called Joshua. There were moments when
Letizia was minded to smother him where he lay beside her, so
horribly did this homuncule reproduce the lineaments of her loathed
husband.
Meanwhile, the factory flourished, Caleb Fuller became the
leading citizen of Brigham and served three times as Mayor. He built
a great gloomy house on the small hill that skirted the mean little
town. He built, too, a great gloomy tabernacle for the Peculiar
Children of God. He was elected chief apostle and sat high up in
view of the congregation on a marble chair. He grew shaggy
whiskers and suffered from piles. He found favour in the eyes of the
Lord, sweating the poor and starving even the cows that gave him
milk. Yes, the renown of Fuller’s Fireworks was spread far and wide.
The factory grew larger year by year. And with it year by year waxed
plumper the belly and the purse of Caleb himself, even as his soul
shrivelled.
In 1851 after twenty years of merciless prosperity Caleb suffered
his first setback by failing to secure the contract for the firework
displays at the Great Exhibition. From the marble chair of the chief
apostle he called upon the Peculiar Children of God to lament that
their Father had temporarily turned away His countenance from
them. Caleb beat his breast and bellowed and groaned, but he did
not rend his garments of the best broadcloth, because that would
have involved his buying new ones. The hulla-balloo in Bethesda
was louder than that in a synagogue on the Day of Atonement, and
after a vociferous prayer-meeting the Peculiar Children of God went
back to their stuffy and secretive little houses, coveting their
neighbours’ wives and their neighbours’ maids, but making the best
of their own to express an unattainable ideal. Horrid stuffy little
bedrooms with blue jets of gas burning dimly through the night-time.
Heavy lumps of humanity snoring beneath heavy counterpanes.
Lascivious backbiting of the coveted wives and maids on greasy
conjugal pillows. Who in all that abode of prurient respectability and
savage industrialism should strip Caleb’s soul bare? Who should not
sympathise with the chief apostle of the Peculiar Children of God?
Yet, strange to say, Caleb found that God’s countenance
continued to be averted from his own. He was still licking the
soreness of his disappointment over the Exhibition fireworks when
one morning in the prime of June his eldest daughter left the great
gloomy house on the hill, never to return. While Caleb stormed at his
wife for not taking better precautions to keep Caterina in bounds, he
was aware that he might as well be storming at a marble statue. He
lacked the imagination to understand that the soul of Letizia had fled
from its imprisonment in the guise of Caterina’s lissom body. But he
did apprehend, however dimly, that henceforth nothing he might say
or do would ever again affect his wife either for good or for ill.
Cold dark eyes beneath black arched brows surveyed him
contemptuously. He had never yet actually struck Letizia; but he
came near to striking her at that moment.
“She wanted to go on the stage.”
“A play-actress! My eldest daughter a play-actress!”
“Alas, neither she nor I can cup those drops of blood she owes to
you. But her soul is hers and mine. You had no part in making that.
Even if you did crawl over my body and eat the heart out of me, you
slug! Do what you like with the others. Make what you can of them.
But Caterina is mine. Caterina is free.”
“As if I had not suffered enough this year,” Caleb groaned.
“Suffered? Did you say that you had suffered?” His wife laughed.
“And what about the sufferings of my Caterina all these years of her
youth?”
“I pray she’ll starve to death,” he went on.
“She was starving to death in this house.”
“Ay, I suppose that’s what the Church folk will be saying next. The
idle, good-for-nothing slanderers! Not content with accusing me of
starving my cows, they’ll be accusing me of starving my children
now. But the dear Lord knows....”
“You poor dull fool,” Letizia broke in, and with one more glance
from her cold dark eyes she left him.
Caterina had as dissolute a career as her father could have feared
and as miserable an end as he could have hoped, for about twelve
years later, after glittering with conspicuous shamelessness amid the
tawdry gilt of the Second Empire, she died in a Paris asylum
prematurely exhausted by drink and dissipation.
“Better to die from without than from within,” said her mother when
the news was brought to Brigham.
“What do you mean by that?” Caleb asked in exasperated
perplexity. “It’s all these French novels you read that makes you talk
that high-flown trash. You talk for the sake of talking, that’s my
opinion. You used to talk like a fool when I first married you, but I
taught you at last to keep your tongue still. Now you’ve begun to talk
again.”
“One changes in thirty-four years, Caleb. Even you have changed.
You were mean and ugly then. But you are much meaner and much
uglier now. However, you have the consolation of seeing your son
Joshua keep pace with you in meanness and in ugliness.”
Joshua Fuller was now twenty-six, an eternal offence to the eyes
of his mother, who perceived in him nothing but a dreadful reminder
of her husband at the same age. That anybody could dare to deplore
Caterina’s life when in Joshua the evidence of her own was before
them enraged Letizia with human crassness. But Joshua was going
to be an asset to Fuller’s Fireworks. Just as his father had perceived
the importance of chlorate of potash in 1829, so now in 1863 did
Joshua perceive the importance of magnesium, and the house of
Fuller was in front of nearly all its rivals in utilising that mineral, with
the result that its brilliant fireworks sold better than ever. The
Guilloché and Salamandre, the Girandole and Spirali of Madame
Oriano, so greatly admired by old moons and bygone multitudes,
would have seemed very dull affairs now. Another gain that Joshua
provided for the business was to urge upon his father to provide for
the further legislation about explosives that sooner or later was
inevitable. With an ill grace Caleb Fuller had complied with the
provisions of the Gunpowder Act of 1860; but, when the great
explosion at Erith occurred a few years later, Joshua insisted that
more must be done to prepare for the inspection of firework
establishments that was bound to follow such a terrific disaster.
Joshua was right, and when the Explosives Act of 1875 was passed
the factory at Brigham had anticipated nearly all its requirements.
By this time Joshua was a widower. In 1865, at the age of twenty-
eight, he had married a pleasant young woman called Susan
Yardley. After presenting him with one boy who was christened
Abraham, she died two years later in producing another who was
christened Caleb after his grandfather.
The elder of these two boys reverted both in appearance and in
disposition to the Oriano stock, and old Mrs. Fuller—she is sixty-
three now and may no longer be called Letizia—took a bitter delight
in never allowing old Mr. Fuller to forget it. She found in the boy, now
a flash of Caterina’s eyes, now a flutter of Madame Oriano’s eyelids.
She would note how much his laugh was like her own long ago, and
she would encourage him at every opportunity to thwart the
solicitude and defy the injunctions of Aunt Achsah and Aunt Thyrza.
When her son protested against the way she applauded Abraham’s
naughtiness, she only laughed.
“Bram’s all right.”
“I wish, mamma, you wouldn’t call him Bram,” Joshua protested.
“It’s so irreverent. I know that you despise the Bible, but the rest of
us almost worship it. I cannot abide this irreligious clipping of
Scriptural names. And it worries poor papa terribly.”
“It won’t worry your father half as much to hear Bram called Bram
as it’ll worry poor little Bram later on to be called Abraham. That
boy’s all right, Josh. He’s the best firework you’ve turned out of this
factory for many a day. So, don’t let Achsah and Thyrza spoil him.”
“They try their best to be strict, mamma.”
“I’m talking about their physic, idiot. They’re a pair of pasty-faced
old maids, and it’s unnatural and unpleasant to let them be for ever
messing about with a capital boy like Bram. Let them physic young
Caleb. He’ll be no loss to the world. Bram might be.”
Joshua threw his eyes up to Heaven and left his unaccountable
mother to her own unaccountable thoughts. He often wondered why
his father had never had her shut up in an asylum. For some time
now she had been collecting outrageous odds and ends of furniture
for her room to which none of the family was allowed access except
by special invitation. Ever since Caterina had run away old Mrs.
Fuller had had a room of her own. But she had been content with an
ordinary bed at first. Now she had procured a monstrous foreign
affair all gilt and Cupids and convolutions. If Joshua had been his
father he would have taken steps to prevent such a waste of her
allowance. He fancied that the old man must be breaking up to allow
such furniture to enter the house.
Not long after the conversation between Joshua and his mother
about Bram, a travelling circus arrived at Brigham on a Sunday
morning. The Peculiar Children of God shivered at such a
profanation of the Sabbath, and Apostle Fuller—in these days a truly
patriarchal figure with his long white food-bespattered beard—
preached from the marble chair on the vileness of these sacrilegious
mountebanks and the pestilent influence any circus must have on a
Christian town. In spite of this denunciation the chief apostle’s own
wife dared to take her elder grandchild on Monday to view from the
best seats obtainable the monstrous performance. They sat so near
the ring that the sawdust and the tan were scattered over them by
the horses’ hoofs. Little Bram, his chin buried in the worn crimson
velvet of the circular barrier, gloated in an ecstasy on the
paradisiacal vision.
“Brava! Bravissima!” old Mrs. Fuller cried loudly when a demoiselle
of the haute école took an extra high fence. “Brava! Bravissima!” she
cried when an equestrienne in pink tights leapt through four blazing
hoops and regained without disarranging one peroxide curl the
shimmering back of her piebald steed.
“Oh, grandmamma,” little Bram gasped when he bade her good
night, “can I be a clown when I’m a man?”
“The difficulty is not to be a clown when one is a man,” she
answered grimly.
“What do you mean, grandmamma?”
“Ah, what?” she sighed.
And in their stuffy and secretive little bedrooms that night the
Peculiar Children of God talked for hours about the disgraceful
amount of leg that those circus women had shown.
“I hear it was extremely suggestive,” said one apostle, smacking
his lips with lecherous disapprobation.
“Was it, indeed, my dear?” the dutiful wife replied, thereby offering
the man of God an opportunity to enlarge upon the prurient topic
before he turned down the gas and got into bed beside her.
“Bram was very naughty to go to the circus, wasn’t he, Aunt
Achsah?” young Caleb asked in a tone of gentle sorrow when his
pasty-faced aunt leaned over that Monday night to lay her wet lips to
his plump pink cheeks.
“Grandpapa was very cross,” Aunt Achsah mournfully replied,
evading the direct answer, but implying much by her expression.
“Gran’papa’s not cross with me, is he, auntie?” young Caleb asked
with an assumption of fervid anxiety.
“No, my dear child, and I hope that you will never, never make
your dear grandfather cross with you.”
“Oh, I won’t, Aunt Achsah,” young Caleb promised, with what Aunt
Achsah told Aunt Thyrza was really and truly the smile of one of
God’s most precious lambs.
“Thyrza, Thyrza, when that blessed little child smiles like that,
nobody could deny him anything. I’m sure his path down this vale of
tears will always be smoothed by that angelic smile.”
She was talking to her sister in the passage just outside young
Caleb’s bedroom—he had already been separated from his elder
brother for fear of corruption—and he heard what she said.
When the footsteps of his aunts died away along the passage, the
fat little boy got out of bed, turned up the gas, and smiled at himself
several times in the looking-glass. Then he retired to bed again,
satisfied of his ability to summon that conquering smile to his aid
whenever he should require it.
CHAPTER V
TINTACKS IN BRIGHAM
On a wet and gusty afternoon in the month of March, 1882, Bram
Fuller, now a stripling of sixteen, sat in one of the dingiest rooms of
that great gloomy house his grandfather had begun to build forty
years before. It looked less stark, now that the evergreen trees had
grown large enough to hide some of its grey rectangularity; but it did
not look any more cheerful in consequence. In some ways it had
seemed less ugly at first, when it stood on top of the mean little hill
and was swept clean by the Cheshire winds. Now its stucco was
stained with great green fronds and arabesques of damp caused by
the drip of the trees and the too close shrubberies of lanky privet and
laurel that sheltered its base. Old Mr. Fuller and his son were both
under the mistaken impression that the trees planted round Lebanon
House—thus had the house been named—were cedars. Whereas
there was not even so much as a deodar among the crowd of
starveling pines and swollen cryptomerias. Noah’s original ark
perched on the summit of Ararat amid the surrounding waters
probably looked a holier abode than Lebanon House above the sea
of Brigham roofs.
The town had grown considerably during half a century, and old
Mr. Fuller had long ago leased the derelict pastures, in which his
cows had tried to eke out a wretched sustenance on chickweed and
sour dock, to accommodate the enterprising builder of rows of little
two-storied houses, the colour of underdone steak. The slopes of the
hill on which the house stood had once been covered with fruit-trees,
but the poisoning of the air by the various chemical factories, which
had increased in number every year, had long made them barren.
Joshua had strongly advised his father to present the useless slopes
to Brigham as a public recreation ground. It was to have been a
good advertisement both for the fireworks and for the civic spirit that
was being fostered by the Peculiar Children of God. As a matter of
fact, Joshua himself had some time ago made up his mind to join the
Church of England as soon as his father died. He was beginning to
think that the Bethesda Tabernacle was not sufficiently up-to-date as
a spiritual centre for Fuller’s Fireworks, and he was more concerned
for the civic impression than the religious importance of the gift. On
this March afternoon, however, the slopes of Lebanon were still a
private domain, for old Mr. Fuller could never bring himself to give
away nine or ten acres of land for nothing. He was much too old to
represent Brigham in Parliament himself, and it never struck him that
Joshua might like to do so.
So, Bram Fuller was able to gaze out of the schoolroom window,
to where, beyond the drenched evergreens hustling one another in
the wind, the drive ran down into Brigham between moribund or
skeleton apple-trees fenced in on either side by those raspberry-
tipped iron railings that his grandfather had bought so cheaply when
the chock-a-block parish churchyard was abolished and an invitingly
empty cemetery was set apart on the other side of the town for the
coming generations of Brigham dead. Bram was still a day-boy at the
grammar school, and as this afternoon was the first half-holiday of
the month he was being allowed to have a friend to tea. Jack
Fleming was late, though. There was no sign of him yet coming up
the slope through the wind and wet. Bram hoped that nothing had
happened to keep him at home. He was so seldom allowed to
entertain friends that Jack’s failure to appear would have been an
overwhelming disappointment. He looked round the schoolroom
dejectedly. Never had it seemed so dingy and comfortless. Never
had that outline portrait of Queen Victoria, filled in not with the
substance of her regal form, but with an account of her life printed in
minute type, seemed such a futile piece of ingenuity; never had the
oilcloth seemed infested with so many crumbs, nor the table-cloth
such a kaleidoscope of jammy stains.
Old Mrs. Fuller had been right when she recognised in the baby
Bram her own race. She and he had their way, and Abraham was
never heard now except in the mouth of the grandfather. Yes, he was
almost a perfect Oriano, having inherited nothing from his father, and
from his mother only her pleasant voice. He was slim, with a clear-
cut profile and fine dark hair; had one observed him idling gracefully
on a sun-splashed piazza, he would have appeared more
appropriate to the setting than to any setting that Brigham could
provide. He was a popular and attractive youth with a talent for
mimicry, and a gay and fluent wit. His young brother, who fortunately
for the enjoyment of Bram and his friend had been invited forth
himself this afternoon, was a perfect Fuller save that he had
inherited from his mother a fresh complexion which at present only
accentuated his plumpness. All the Fuller characteristics were there
—the greedy grey eyes, the podgy white hands, the fat rump and
spindle legs, the full wet lips and slimy manner. To all this young
Caleb could add his own smile of innocent candour when it suited his
purpose to produce it. At school he was notorious as a toady and a
sneak, but he earned a tribute of respect from the sons of a
commercial community by his capacity for swopping to his own
advantage and by his never failing stock of small change, which he
was always willing to lend at exorbitant interest on good security.
Bram was badly in debt to his young brother at the present moment,
and this added something to the depression of the black March
afternoon, though that was lightened at last by the tardy arrival of his
expected friend with the news that Blundell’s Diorama had arrived in
Brigham and would exhibit itself at seven o’clock.
“We must jolly well go, Bramble,” Jack declared.
Bram shook his head despondently.
“No chink!”
“Can’t you borrow some from young Caleb?”
“I owe him two and threepence halfpenny already, and he’s got my
best whalebone-splice bat as a security till I pay him back.”
“Good Lord, and I’ve only got sixpence,” Jack Fleming groaned.
“Anyway, it’s no use,” Bram went on. “The governor wouldn’t let
me go into Brigham on a Saturday night.”
“Can’t you find some excuse?”
Bram pondered for a few seconds.
“I might get my grandmater to help.”
“Well, buck up, Bramble. It’s a spiffing show, I hear. They’ve got
two girls with Italian names who play the guitar or something. We
don’t often get a chance of a decent evening in Brigham.”
“You’re right, Jack. All serene! Then I’ll have a try with the
grandmater. She’s such an old fizzer that she might manage it.”
Bram went up cautiously to old Mrs. Fuller’s room. She was
seventy now, but still able to hate fiercely her octogenarian husband
who was for ever browsing among dusty commentaries on the Old
Testament nowadays, and extracting from the tortuous fretwork of
bookworms such indications of the Divine purpose as the exact date
and hour of the Day of Judgment. He was usually clad in a moth-
eaten velveteen dressing-gown and a smoking cap of quilted black
silk with a draggled crimson tassel. The latter must have been worn
as a protection to his bald and scaly head, because not a puff of
tobacco smoke had ever been allowed to contend with the odour of
stale food that permeated Lebanon House from cellar to garret.
The old lady was sitting by the fire in her rococo parlour, reading
Alphonse Daudet’s new book. Her hawk’s face seemed to be not so
much wrinkled as finely cracked like old ivory. Over her shoulders
she wore a wrap of rose and silver brocade.
“Why, Bram, I thought you were entertaining visitors this
afternoon.”
“I am. He’s downstairs in the schoolroom. Jack Fleming, I mean.”
“Is that a son of that foxy-faced solicitor in High Street?”
Bram nodded.
“But Jack’s rather decent. I think you’d like him, grandmamma.”
“Ah, I’m too old to begin liking new people.”
Bram kicked his legs together, trying to make up his mind what line
to adopt for enlisting the old lady’s sympathy.
“Blundell’s Diorama is here,” he announced at last.
Welcome to our website – the ideal destination for book lovers and
knowledge seekers. With a mission to inspire endlessly, we offer a
vast collection of books, ranging from classic literary works to
specialized publications, self-development books, and children's
literature. Each book is a new journey of discovery, expanding
knowledge and enriching the soul of the reade

Our website is not just a platform for buying books, but a bridge
connecting readers to the timeless values of culture and wisdom. With
an elegant, user-friendly interface and an intelligent search system,
we are committed to providing a quick and convenient shopping
experience. Additionally, our special promotions and home delivery
services ensure that you save time and fully enjoy the joy of reading.

Let us accompany you on the journey of exploring knowledge and


personal growth!

textbookfull.com

You might also like