Browse Source

Merge branch 'master' of https://github.com/bitcoin/bitcoin

Conflicts:
	src/main.cpp
pull/1/head
Wladimir J. van der Laan 11 years ago
parent
commit
7a15d4ff67
  1. 38
      contrib/boost-win32.yml
  2. 77
      contrib/gitian-win32.yml
  3. 36
      contrib/gitian.yml
  4. 6
      contrib/pyminer/README
  5. 32
      contrib/pyminer/example-config.cfg
  6. 252
      contrib/pyminer/pyminer.py
  7. 4
      contrib/wx-patches/README
  8. 86
      contrib/wx-patches/toplevel.cpp.diff
  9. 9
      contrib/wx-patches/toplevel.h.diff
  10. 40
      contrib/wxwidgets-win32.yml
  11. 42
      contrib/wxwidgets.yml
  12. 48
      doc/README
  13. 36
      doc/build-msw.txt
  14. 18
      doc/build-osx.txt
  15. 21
      doc/build-unix.txt
  16. 44
      doc/coding.txt
  17. 636
      locale/pl/LC_MESSAGES/bitcoin.po
  18. 642
      src/bitcoinrpc.cpp
  19. 3
      src/db.cpp
  20. 21
      src/keystore.cpp
  21. 54
      src/keystore.h
  22. 24
      src/main.cpp
  23. 14
      src/main.h
  24. 60
      src/makefile.linux-mingw
  25. 67
      src/makefile.mingw
  26. 39
      src/makefile.osx
  27. 39
      src/makefile.unix
  28. 50
      src/makefile.vc
  29. 128
      src/net.cpp
  30. 405
      src/net.h
  31. 312
      src/protocol.cpp
  32. 150
      src/protocol.h
  33. 102
      src/script.cpp
  34. 11
      src/serialize.h
  35. 381
      src/ui.cpp
  36. 8
      src/util.cpp
  37. 8
      src/util.h
  38. 239
      src/wallet.cpp
  39. 17
      src/wallet.h

38
contrib/boost-win32.yml

@ -0,0 +1,38 @@ @@ -0,0 +1,38 @@
---
name: "boost"
suites:
- "lucid"
architectures:
- "i386"
packages:
- "mingw32"
- "faketime"
- "zip"
reference_datetime: "2011-01-30 00:00:00"
remotes: []
files:
- "boost_1_47_0.tar.bz2"
script: |
TMPDIR="$HOME/tmpdir"
mkdir -p $TMPDIR/bin/$GBUILD_BITS $TMPDIR/include
tar xjf boost_1_47_0.tar.bz2
cd boost_1_47_0
echo "using gcc : 4.4 : i586-mingw32msvc-g++
:
<rc>i586-mingw32msvc-windres
<archiver>i586-mingw32msvc-ar
<cxxflags>-frandom-seed=boost1
;" > user-config.jam
./bootstrap.sh --without-icu
./bjam toolset=gcc target-os=windows threadapi=win32 threading=multi variant=release link=static --user-config=user-config.jam --without-mpi --without-python -sNO_BZIP2=1 -sNO_ZLIB=1 --layout=tagged --build-type=complete $MAKEOPTS stage
for lib in chrono date_time exception filesystem graph iostreams math_c99f math_c99l math_c99 math_tr1f math_tr1l math_tr1 prg_exec_monitor program_options random regex serialization signals system test_exec_monitor thread_win32 unit_test_framework wave wserialization; do
mkdir $lib
(cd $lib ; ar xf ../stage/lib/libboost_${lib}-mt-s.a)
mv $lib $TMPDIR/bin/$GBUILD_BITS
done
cp -a boost $TMPDIR/include
cd $TMPDIR
export LD_PRELOAD=/usr/lib/faketime/libfaketime.so.1
export FAKETIME=$REFERENCE_DATETIME
zip -r boost-win32-1.47.0-gitian.zip *
cp boost-win32-1.47.0-gitian.zip $OUTDIR

77
contrib/gitian-win32.yml

@ -9,25 +9,44 @@ packages: @@ -9,25 +9,44 @@ packages:
- "git-core"
- "unzip"
- "nsis"
- "faketime"
reference_datetime: "2011-01-30 00:00:00"
remotes:
- "url": "https://github.com/bitcoin/bitcoin.git"
"dir": "bitcoin"
files:
- "wxWidgets-2.9.1.tar.bz2"
- "boost_1_43_0.tar.bz2"
- "wxwidgets-win32-2.9.2-gitian.zip"
- "boost-win32-1.47.0-gitian.zip"
- "openssl-1.0.0d.tar.gz"
- "db-4.7.25.NC.tar.gz"
- "upnpc-exe-win32-20110215.zip"
- "miniupnpc-1.5.20110215.tar.gz"
- "WSPiApi.h"
- "db-4.8.30.NC.tar.gz"
- "miniupnpc-1.6.tar.gz"
script: |
#
tar xjf wxWidgets-2.9.1.tar.bz2
cd wxWidgets-2.9.1
./configure --host=i586-mingw32msvc --build=i686-linux --disable-shared --enable-monolithic --without-libpng --disable-svg
perl -i -p -e "s/__TIME__/\"$REFERENCE_TIME\"/;s/__DATE__/\"$REFERENCE_DATE\"/" include/wx/chartype.h
make $MAKEOPTS
mkdir wxWidgets-2.9.2
cd wxWidgets-2.9.2
mkdir lib
unzip ../wxwidgets-win32-2.9.2-gitian.zip
cd bin/$GBUILD_BITS
for lib in wx_mswu; do
i586-mingw32msvc-ar rc ../../lib/lib${lib}-2.9-i586-mingw32msvc.a $lib/*.o
i586-mingw32msvc-ranlib ../../lib/lib${lib}-2.9-i586-mingw32msvc.a
done
cp -a wx ../../lib
cd ../..
mv include/wx-2.9/wx include
cd ..
#
mkdir boost_1_47_0
cd boost_1_47_0
mkdir -p stage/lib
unzip ../boost-win32-1.47.0-gitian.zip
cd bin/$GBUILD_BITS
for lib in *; do
i586-mingw32msvc-ar rc ../../stage/lib/libboost_${lib}-mt-s.a $lib/*.o
i586-mingw32msvc-ranlib ../../stage/lib/libboost_${lib}-mt-s.a
done
cd ../..
mv include/boost .
cd ..
#
tar xzf openssl-1.0.0d.tar.gz
@ -36,33 +55,19 @@ script: | @@ -36,33 +55,19 @@ script: |
make
cd ..
#
tar xzf db-4.7.25.NC.tar.gz
cd db-4.7.25.NC/build_unix
tar xzf db-4.8.30.NC.tar.gz
cd db-4.8.30.NC/build_unix
../dist/configure --enable-mingw --enable-cxx --host=i586-mingw32msvc CFLAGS="-I/usr/i586-mingw32msvc/include"
make $MAKEOPTS
cd ../..
#
tar xjf boost_1_43_0.tar.bz2
cd boost_1_43_0
echo "using gcc : 4.4 : i586-mingw32msvc-g++
:
<rc>i586-mingw32msvc-windres
<archiver>i586-mingw32msvc-ar
;" > user-config.jam
./bootstrap.sh --without-icu
./bjam toolset=gcc target-os=windows threadapi=win32 threading=multi --user-config=user-config.jam --without-mpi --without-python -sNO_BZIP2=1 -sNO_ZLIB=1 --layout=tagged --build-type=complete $MAKEOPTS stage
tar xzf miniupnpc-1.6.tar.gz
cd miniupnpc-1.6
sed 's/dllwrap -k --driver-name gcc/$(DLLWRAP) -k --driver-name $(CC)/' -i Makefile.mingw
sed 's|wingenminiupnpcstrings $< $@|./wingenminiupnpcstrings $< $@|' -i Makefile.mingw
make -f Makefile.mingw DLLWRAP=i586-mingw32msvc-dllwrap CC=i586-mingw32msvc-gcc AR=i586-mingw32msvc-ar
cd ..
#
mkdir upnpc-exe-win32-20110215
cd upnpc-exe-win32-20110215
unzip ../upnpc-exe-win32-20110215.zip
mkdir miniupnpc
cd miniupnpc
tar xzf ../../miniupnpc-1.5.20110215.tar.gz
mv ./miniupnpc-1.5.20110215/* ./
cd ../..
#
cp WSPiApi.h $HOME/build
mv miniupnpc-1.6 miniupnpc
#
cd bitcoin
mkdir -p $OUTDIR/src
@ -72,8 +77,10 @@ script: | @@ -72,8 +77,10 @@ script: |
cp $OUTDIR/src/doc/README_windows.txt $OUTDIR/readme.txt
cp $OUTDIR/src/COPYING $OUTDIR/license.txt
cd src
sed 's/$(DEBUGFLAGS)//' < makefile.linux-mingw > makefile.linux-mingw.2 && mv makefile.linux-mingw.2 makefile.linux-mingw
sed 's|//#include <WSPiApi.h>|#include <WSPiApi.h>|' < net.cpp > net.cpp.2 && mv net.cpp.2 net.cpp
sed 's/$(DEBUGFLAGS)/-frandom-seed=bitcoin/' -i makefile.linux-mingw
export LD_PRELOAD=/usr/lib/faketime/libfaketime.so.1
export FAKETIME=$REFERENCE_DATETIME
export TZ=UTC
make -f makefile.linux-mingw $MAKEOPTS DEPSDIR=$HOME/build bitcoin.exe USE_UPNP=1
make -f makefile.linux-mingw $MAKEOPTS DEPSDIR=$HOME/build bitcoind.exe USE_UPNP=0
i586-mingw32msvc-strip bitcoin.exe

36
contrib/gitian.yml

@ -6,40 +6,40 @@ architectures: @@ -6,40 +6,40 @@ architectures:
- "i386"
- "amd64"
packages:
- "libdb4.7++-dev"
- "libdb4.8++-dev"
- "libxxf86vm-dev"
- "libgtk2.0-dev"
- "libboost-all-dev"
- "libssl-dev"
- "git-core"
- "unzip"
reference_datetime: "2011-01-30 00:00:00"
remotes:
- "url": "https://github.com/bitcoin/bitcoin.git"
"dir": "bitcoin"
files:
- "wxWidgets-2.9.1.tar.bz2"
- "miniupnpc-1.5.tar.gz"
- "toplevel.h.diff"
- "toplevel.cpp.diff"
- "wxWidgets-2.9.2-gitian.zip"
- "miniupnpc-1.6.tar.gz"
script: |
INSTDIR="$HOME/install"
export LIBRARY_PATH="$INSTDIR/lib"
#
tar xzf miniupnpc-1.5.tar.gz
cd miniupnpc-1.5
tar xzf miniupnpc-1.6.tar.gz
cd miniupnpc-1.6
INSTALLPREFIX=$INSTDIR make $MAKEOPTS install
cd ..
#
tar xjf wxWidgets-2.9.1.tar.bz2
cd wxWidgets-2.9.1
cd include/wx/gtk
patch < ../../../../toplevel.h.diff
cd ../../../src/gtk
patch < ../../../toplevel.cpp.diff
cd ../..
./configure --prefix=$INSTDIR --enable-monolithic --disable-shared
perl -i -p -e "s/__TIME__/\"$REFERENCE_TIME\"/;s/__DATE__/\"$REFERENCE_DATE\"/" include/wx/chartype.h
make $MAKEOPTS install
mkdir -p $INSTDIR/bin $INSTDIR/lib/wx $INSTDIR/include
mkdir wxWidgets-2.9.2
cd wxWidgets-2.9.2
unzip ../wxWidgets-2.9.2-gitian.zip
cp -a bin/$GBUILD_BITS/wx/config/gtk2-unicode-static-2.9 $INSTDIR/bin/wx-config
for lib in wx_gtk2u wxregexu wxtiff; do
ar rc $INSTDIR/lib/lib${lib}-2.9.a bin/$GBUILD_BITS/$lib/*.o
ranlib $INSTDIR/lib/lib${lib}-2.9.a
done
cp -a include/wx-2.9/* $INSTDIR/include
cp -a bin/$GBUILD_BITS/wx/include $INSTDIR/lib/wx
cd ..
#
cd bitcoin
@ -50,7 +50,7 @@ script: | @@ -50,7 +50,7 @@ script: |
cp $OUTDIR/src/doc/README $OUTDIR
cp $OUTDIR/src/COPYING $OUTDIR
cd src
sed 's/$(DEBUGFLAGS)//' < makefile.unix > makefile.unix.2 && mv makefile.unix.2 makefile.unix
sed 's/$(DEBUGFLAGS)//' -i makefile.unix
PATH=$INSTDIR/bin:$PATH make -f makefile.unix CXX="g++ -I$INSTDIR/include -L$INSTDIR/lib" $MAKEOPTS bitcoin USE_UPNP=1
PATH=$INSTDIR/bin:$PATH make -f makefile.unix CXX="g++ -I$INSTDIR/include -L$INSTDIR/lib" $MAKEOPTS bitcoind USE_UPNP=0
mkdir -p $OUTDIR/bin/$GBUILD_BITS

6
contrib/pyminer/README

@ -0,0 +1,6 @@ @@ -0,0 +1,6 @@
This is a 'getwork' CPU mining client for bitcoin.
It is pure-python, and therefore very, very slow. The purpose is to
provide a reference implementation of a miner, for study.

32
contrib/pyminer/example-config.cfg

@ -0,0 +1,32 @@ @@ -0,0 +1,32 @@
#
# RPC login details
#
host=127.0.0.1
port=8332
rpcuser=myusername
rpcpass=mypass
#
# mining details
#
threads=4
# periodic rate for requesting new work, if solution not found
scantime=60
#
# misc.
#
# not really used right now
logdir=/tmp/pyminer
# set to 1, to enable hashmeter output
hashmeter=0

252
contrib/pyminer/pyminer.py

@ -0,0 +1,252 @@ @@ -0,0 +1,252 @@
#!/usr/bin/python
#
# Copyright (c) 2011 The Bitcoin developers
# Distributed under the MIT/X11 software license, see the accompanying
# file license.txt or http://www.opensource.org/licenses/mit-license.php.
#
import time
import json
import pprint
import hashlib
import struct
import re
import base64
import httplib
import sys
from multiprocessing import Process
ERR_SLEEP = 15
MAX_NONCE = 1000000L
settings = {}
pp = pprint.PrettyPrinter(indent=4)
class BitcoinRPC:
OBJID = 1
def __init__(self, host, port, username, password):
authpair = "%s:%s" % (username, password)
self.authhdr = "Basic %s" % (base64.b64encode(authpair))
self.conn = httplib.HTTPConnection(host, port, False, 30)
def rpc(self, method, params=None):
self.OBJID += 1
obj = { 'version' : '1.1',
'method' : method,
'id' : self.OBJID }
if params is None:
obj['params'] = []
else:
obj['params'] = params
self.conn.request('POST', '/', json.dumps(obj),
{ 'Authorization' : self.authhdr,
'Content-type' : 'application/json' })
resp = self.conn.getresponse()
if resp is None:
print "JSON-RPC: no response"
return None
body = resp.read()
resp_obj = json.loads(body)
if resp_obj is None:
print "JSON-RPC: cannot JSON-decode body"
return None
if 'error' in resp_obj and resp_obj['error'] != None:
return resp_obj['error']
if 'result' not in resp_obj:
print "JSON-RPC: no result in object"
return None
return resp_obj['result']
def getblockcount(self):
return self.rpc('getblockcount')
def getwork(self, data=None):
return self.rpc('getwork', data)
def uint32(x):
return x & 0xffffffffL
def bytereverse(x):
return uint32(( ((x) << 24) | (((x) << 8) & 0x00ff0000) |
(((x) >> 8) & 0x0000ff00) | ((x) >> 24) ))
def bufreverse(in_buf):
out_words = []
for i in range(0, len(in_buf), 4):
word = struct.unpack('@I', in_buf[i:i+4])[0]
out_words.append(struct.pack('@I', bytereverse(word)))
return ''.join(out_words)
def wordreverse(in_buf):
out_words = []
for i in range(0, len(in_buf), 4):
out_words.append(in_buf[i:i+4])
out_words.reverse()
return ''.join(out_words)
class Miner:
def __init__(self, id):
self.id = id
self.max_nonce = MAX_NONCE
def work(self, datastr, targetstr):
# decode work data hex string to binary
static_data = datastr.decode('hex')
static_data = bufreverse(static_data)
# the first 76b of 80b do not change
blk_hdr = static_data[:76]
# decode 256-bit target value
targetbin = targetstr.decode('hex')
targetbin = targetbin[::-1] # byte-swap and dword-swap
targetbin_str = targetbin.encode('hex')
target = long(targetbin_str, 16)
# pre-hash first 76b of block header
static_hash = hashlib.sha256()
static_hash.update(blk_hdr)
for nonce in xrange(self.max_nonce):
# encode 32-bit nonce value
nonce_bin = struct.pack("<I", nonce)
# hash final 4b, the nonce value
hash1_o = static_hash.copy()
hash1_o.update(nonce_bin)
hash1 = hash1_o.digest()
# sha256 hash of sha256 hash
hash_o = hashlib.sha256()
hash_o.update(hash1)
hash = hash_o.digest()
# quick test for winning solution: high 32 bits zero?
if hash[-4:] != '\0\0\0\0':
continue
# convert binary hash to 256-bit Python long
hash = bufreverse(hash)
hash = wordreverse(hash)
hash_str = hash.encode('hex')
l = long(hash_str, 16)
# proof-of-work test: hash < target
if l < target:
print time.asctime(), "PROOF-OF-WORK found: %064x" % (l,)
return (nonce + 1, nonce_bin)
else:
print time.asctime(), "PROOF-OF-WORK false positive %064x" % (l,)
# return (nonce + 1, nonce_bin)
return (nonce + 1, None)
def submit_work(self, rpc, original_data, nonce_bin):
nonce_bin = bufreverse(nonce_bin)
nonce = nonce_bin.encode('hex')
solution = original_data[:152] + nonce + original_data[160:256]
param_arr = [ solution ]
result = rpc.getwork(param_arr)
print time.asctime(), "--> Upstream RPC result:", result
def iterate(self, rpc):
work = rpc.getwork()
if work is None:
time.sleep(ERR_SLEEP)
return
if 'data' not in work or 'target' not in work:
time.sleep(ERR_SLEEP)
return
time_start = time.time()
(hashes_done, nonce_bin) = self.work(work['data'],
work['target'])
time_end = time.time()
time_diff = time_end - time_start
self.max_nonce = long(
(hashes_done * settings['scantime']) / time_diff)
if self.max_nonce > 0xfffffffaL:
self.max_nonce = 0xfffffffaL
if settings['hashmeter']:
print "HashMeter(%d): %d hashes, %.2f Khash/sec" % (
self.id, hashes_done,
(hashes_done / 1000.0) / time_diff)
if nonce_bin is not None:
self.submit_work(rpc, work['data'], nonce_bin)
def loop(self):
rpc = BitcoinRPC(settings['host'], settings['port'],
settings['rpcuser'], settings['rpcpass'])
if rpc is None:
return
while True:
self.iterate(rpc)
def miner_thread(id):
miner = Miner(id)
miner.loop()
if __name__ == '__main__':
if len(sys.argv) != 2:
print "Usage: pyminer.py CONFIG-FILE"
sys.exit(1)
f = open(sys.argv[1])
for line in f:
# skip comment lines
m = re.search('^\s*#', line)
if m:
continue
# parse key=value lines
m = re.search('^(\w+)\s*=\s*(\S.*)$', line)
if m is None:
continue
settings[m.group(1)] = m.group(2)
f.close()
if 'host' not in settings:
settings['host'] = '127.0.0.1'
if 'port' not in settings:
settings['port'] = 8332
if 'threads' not in settings:
settings['threads'] = 1
if 'hashmeter' not in settings:
settings['hashmeter'] = 0
if 'scantime' not in settings:
settings['scantime'] = 30L
if 'rpcuser' not in settings or 'rpcpass' not in settings:
print "Missing username and/or password in cfg file"
sys.exit(1)
settings['port'] = int(settings['port'])
settings['threads'] = int(settings['threads'])
settings['hashmeter'] = int(settings['hashmeter'])
settings['scantime'] = long(settings['scantime'])
thr_list = []
for thr_id in range(settings['threads']):
p = Process(target=miner_thread, args=(thr_id,))
p.start()
thr_list.append(p)
time.sleep(1) # stagger threads
print settings['threads'], "mining threads started"
print time.asctime(), "Miner Starts - %s:%s" % (settings['host'], settings['port'])
try:
for thr_proc in thr_list:
thr_proc.join()
except KeyboardInterrupt:
pass
print time.asctime(), "Miner Stops - %s:%s" % (settings['host'], settings['port'])

4
contrib/wx-patches/README

@ -1,4 +0,0 @@ @@ -1,4 +0,0 @@
This folder contains two patches which are applied to wxWidgets
2.9.1 before building the wxWidgets which is used for release
versions of bitcoin. They make the GUI show up on newer OSs
with new libgtks, such as Ubuntu 11.04.

86
contrib/wx-patches/toplevel.cpp.diff

@ -1,86 +0,0 @@ @@ -1,86 +0,0 @@
--- /wxWidgets/trunk/src/gtk/toplevel.cpp (revision 67326)
+++ /wxWidgets/trunk/src/gtk/toplevel.cpp (revision 67496)
@@ -72,4 +72,8 @@
// send any activate events at all
static int g_sendActivateEvent = -1;
+
+// Whether _NET_REQUEST_FRAME_EXTENTS support is working
+// 0 == not tested yet, 1 == working, 2 == broken
+static int gs_requestFrameExtentsStatus;
//-----------------------------------------------------------------------------
@@ -432,4 +436,12 @@
if (event->state == GDK_PROPERTY_NEW_VALUE && event->atom == property)
{
+ if (win->m_netFrameExtentsTimerId)
+ {
+ // WM support for _NET_REQUEST_FRAME_EXTENTS is working
+ gs_requestFrameExtentsStatus = 1;
+ g_source_remove(win->m_netFrameExtentsTimerId);
+ win->m_netFrameExtentsTimerId = 0;
+ }
+
wxSize decorSize = win->m_decorSize;
int left, right, top, bottom;
@@ -439,4 +451,22 @@
win->GTKUpdateDecorSize(decorSize);
}
+ return false;
+}
+}
+
+extern "C" {
+static gboolean request_frame_extents_timeout(void* data)
+{
+ // WM support for _NET_REQUEST_FRAME_EXTENTS is broken
+ gs_requestFrameExtentsStatus = 2;
+ gdk_threads_enter();
+ wxTopLevelWindowGTK* win = static_cast<wxTopLevelWindowGTK*>(data);
+ win->m_netFrameExtentsTimerId = 0;
+ wxSize decorSize = win->m_decorSize;
+ int left, right, top, bottom;
+ if (wxGetFrameExtents(gtk_widget_get_window(win->m_widget), &left, &right, &top, &bottom))
+ decorSize.Set(left + right, top + bottom);
+ win->GTKUpdateDecorSize(decorSize);
+ gdk_threads_leave();
return false;
}
@@ -459,4 +489,5 @@
m_deferShowAllowed = true;
m_updateDecorSize = true;
+ m_netFrameExtentsTimerId = 0;
m_urgency_hint = -2;
@@ -811,5 +842,6 @@
if (deferShow)
{
- deferShow = m_deferShowAllowed && !GTK_WIDGET_REALIZED(m_widget);
+ deferShow = gs_requestFrameExtentsStatus != 2 &&
+ m_deferShowAllowed && !gtk_widget_get_realized(m_widget);
if (deferShow)
{
@@ -829,11 +861,4 @@
// GetSize()/SetSize() because it makes window bigger between each
// restore and save.
- m_updateDecorSize = deferShow;
- }
- if (deferShow)
- {
- // Fluxbox support for _NET_REQUEST_FRAME_EXTENTS is broken
- const char* name = gdk_x11_screen_get_window_manager_name(screen);
- deferShow = strcmp(name, "Fluxbox") != 0;
m_updateDecorSize = deferShow;
}
@@ -875,4 +900,12 @@
(XEvent*)&xevent);
+ if (gs_requestFrameExtentsStatus == 0)
+ {
+ // if WM does not respond to request within 1 second,
+ // we assume support for _NET_REQUEST_FRAME_EXTENTS is not working
+ m_netFrameExtentsTimerId =
+ g_timeout_add(1000, request_frame_extents_timeout, this);
+ }
+
// defer calling gtk_widget_show()
m_isShown = true;

9
contrib/wx-patches/toplevel.h.diff

@ -1,9 +0,0 @@ @@ -1,9 +0,0 @@
--- /wxWidgets/trunk/include/wx/gtk/toplevel.h (revision 65373)
+++ /wxWidgets/trunk/include/wx/gtk/toplevel.h (revision 67496)
@@ -114,4 +114,6 @@
// wxUSER_ATTENTION_ERROR difference, -2 for no hint, -1 for ERROR hint, rest for GtkTimeout handle.
int m_urgency_hint;
+ // timer for detecting WM with broken _NET_REQUEST_FRAME_EXTENTS handling
+ unsigned m_netFrameExtentsTimerId;
// return the size of the window without WM decorations

40
contrib/wxwidgets-win32.yml

@ -0,0 +1,40 @@ @@ -0,0 +1,40 @@
---
name: "wxwidgets"
suites:
- "lucid"
architectures:
- "i386"
packages:
- "mingw32"
- "faketime"
- "zip"
reference_datetime: "2011-01-30 00:00:00"
remotes: []
files:
- "wxWidgets-2.9.2.tar.bz2"
script: |
INSTDIR="$HOME/install"
TMPDIR="$HOME/tmpdir"
export LIBRARY_PATH="$INSTDIR/lib"
#
tar xjf wxWidgets-2.9.2.tar.bz2
cd wxWidgets-2.9.2
CXXFLAGS=-frandom-seed=wx1 ./configure --host=i586-mingw32msvc --build=i686-linux --prefix=$INSTDIR --disable-shared --enable-monolithic --without-libpng --disable-svg
perl -i -p -e "s/__TIME__/\"$REFERENCE_TIME\"/;s/__DATE__/\"$REFERENCE_DATE\"/" include/wx/chartype.h
make $MAKEOPTS install
mkdir $TMPDIR
cd $TMPDIR
cp -af $INSTDIR/include .
mkdir -p $TMPDIR/bin/$GBUILD_BITS
cd $TMPDIR/bin/$GBUILD_BITS
cp -af $INSTDIR/lib/wx .
for lib in wx_mswu; do
mkdir $lib
(cd $lib ; ar xf $INSTDIR/lib/lib${lib}-2.9-i586-mingw32msvc.a)
done
chmod -R +w $TMPDIR
cd $TMPDIR
export LD_PRELOAD=/usr/lib/faketime/libfaketime.so.1
export FAKETIME=$REFERENCE_DATETIME
zip -r wxwidgets-win32-2.9.2-gitian.zip *
cp wxwidgets-win32-2.9.2-gitian.zip $OUTDIR

42
contrib/wxwidgets.yml

@ -0,0 +1,42 @@ @@ -0,0 +1,42 @@
---
name: "wxwidgets"
suites:
- "lucid"
architectures:
- "i386"
- "amd64"
packages:
- "libxxf86vm-dev"
- "libgtk2.0-dev"
- "faketime"
- "zip"
reference_datetime: "2011-01-30 00:00:00"
remotes: []
files:
- "wxWidgets-2.9.2.tar.bz2"
script: |
INSTDIR="$HOME/install"
TMPDIR="$HOME/tmpdir"
export LIBRARY_PATH="$INSTDIR/lib"
#
tar xjf wxWidgets-2.9.2.tar.bz2
cd wxWidgets-2.9.2
./configure --prefix=$INSTDIR --enable-monolithic --disable-shared
perl -i -p -e "s/__TIME__/\"$REFERENCE_TIME\"/;s/__DATE__/\"$REFERENCE_DATE\"/" include/wx/chartype.h
make $MAKEOPTS install
mkdir $TMPDIR
cd $TMPDIR
cp -af $INSTDIR/include .
mkdir -p $TMPDIR/bin/$GBUILD_BITS
cd $TMPDIR/bin/$GBUILD_BITS
cp -af $INSTDIR/lib/wx .
for lib in wxtiff wxregexu wx_gtk2u; do
mkdir $lib
(cd $lib ; ar xf $INSTDIR/lib/lib${lib}-2.9.a)
done
chmod -R +w $TMPDIR
cd $TMPDIR
export LD_PRELOAD=/usr/lib/faketime/libfaketime.so.1
export FAKETIME=$REFERENCE_DATETIME
zip -r wxWidgets-2.9.2-gitian.zip *
cp wxWidgets-2.9.2-gitian.zip $OUTDIR

48
doc/README

@ -36,7 +36,7 @@ every time you wish to send Bitcoins. If you lose this passphrase, @@ -36,7 +36,7 @@ every time you wish to send Bitcoins. If you lose this passphrase,
you will lose access to spend all of the bitcoins in your wallet,
no one, not even the Bitcoin developers can recover your Bitcoins.
This means you are responsible for your own security, store your
password in a secure location and do not forget it.
passphrase in a secure location and do not forget it.
Remember that the encryption built into bitcoin only encrypts the
actual keys which are required to send your bitcoins, not the full
@ -57,7 +57,7 @@ If everything goes fine, delete the backup and enjoy your encrypted @@ -57,7 +57,7 @@ If everything goes fine, delete the backup and enjoy your encrypted
wallet. Note that once you encrypt your wallet, you will never be
able to go back to a version of the Bitcoin client older than 0.4.
Keep in mind that you are always responsible for you own security.
Keep in mind that you are always responsible for your own security.
All it takes is a slightly more advanced wallet-stealing trojan which
installs a keylogger to steal your wallet passphrase as you enter it
in addition to your wallet file and you have lost all your Bitcoins.
@ -67,6 +67,50 @@ entering your wallet passphrase in the Bitcoin client and using the @@ -67,6 +67,50 @@ entering your wallet passphrase in the Bitcoin client and using the
same passphrase only as your wallet passphrase.
Technical details of wallet encryption
--------------------------------------
Wallet encryption uses AES-256-CBC to encrypt only the private keys
that are held in a wallet. The keys are encrypted with a master key
which is entirely random. This master key is then encrypted with
AES-256-CBC with a key derived from the passphrase using SHA512 and
OpenSSL's EVP_BytesToKey and a dynamic number of rounds determined by
the speed of the machine which does the initial encryption (and is
updated based on the speed of a computer which does a subsequent
passphrase change). Although the underlying code supports multiple
encrypted copies of the same master key (and thus multiple passphrases)
the client does not yet have a method to add additional passphrases.
At runtime, the client loads the wallet as it normally would, however
the keystore stores the keys in encrypted form. When the passphrase
is required (to top up keypool or send coins) it will either be queried
by a GUI prompt, or must first be entered with the walletpassphrase
RPC command. This will change the wallet to "unlocked" state where the
unencrypted master key is stored in memory (in the case of GUI, only for
long enough to complete the requested operation, in RPC, for as long as
is specified by the second parameter to walletpassphrase). The wallet is
then locked (or can be manually locked using the walletlock RPC command)
and the unencrypted master key is removed from memory.
Implementation details of wallet encryption
-------------------------------------------
When the wallet is locked, calls to sendtoaddress, sendfrom, sendmany,
and keypoolrefill will return Error -13: "Error: Please enter the wallet
passphrase with walletpassphrase first."
When the wallet is unlocked, calls to walletpassphrase will fail.
When a wallet is encrypted, the passphrase is required to top up the
keypool, thus, if the passphrase is rarely entered, it is possible that
keypool might run out. In this case, the default key will be used as the
target for payouts for mining, and calls to getnewaddress and getaccount
address will return an error. In order to prevent such cases, the keypool
is automatically refilled when walletpassphrase is called with a correct
passphrase and when topupkeypool is called (while the wallet is unlocked).
Note that the keypool continues to be topped up on various occasions when
a new key from pool is used and the wallet is unlocked (or unencrypted).
See the documentation at the bitcoin wiki:
https://en.bitcoin.it/wiki/Main_Page

36
doc/build-msw.txt

@ -27,11 +27,11 @@ Dependencies @@ -27,11 +27,11 @@ Dependencies
Libraries you need to download separately and build:
default path download
wxWidgets \wxwidgets-2.9.1-mgw http://www.wxwidgets.org/downloads/
wxWidgets \wxwidgets-2.9.2-mgw http://www.wxwidgets.org/downloads/
OpenSSL \openssl-1.0.0d-mgw http://www.openssl.org/source/
Berkeley DB \db-4.7.25.NC-mgw http://www.oracle.com/technology/software/products/berkeley-db/index.html
Boost \boost-1.43.0-mgw http://www.boost.org/users/download/
miniupnpc \upnpc-exe-win32-20110215 http://miniupnp.tuxfamily.org/files/
Berkeley DB \db-4.8.30.NC-mgw http://www.oracle.com/technology/software/products/berkeley-db/index.html
Boost \boost-1.47.0-mgw http://www.boost.org/users/download/
miniupnpc \miniupnpc-1.6-mgw http://miniupnp.tuxfamily.org/files/
Their licenses:
wxWidgets LGPL 2.1 with very liberal exceptions
@ -41,11 +41,11 @@ Boost MIT-like license @@ -41,11 +41,11 @@ Boost MIT-like license
miniupnpc New (3-clause) BSD license
Versions used in this release:
wxWidgets 2.9.1
wxWidgets 2.9.2
OpenSSL 1.0.0d
Berkeley DB 4.7.25.NC
Boost 1.43.0
miniupnpc 1.5-20110215
Berkeley DB 4.8.30.NC
Boost 1.47.0
miniupnpc 1.6
Notes
@ -57,7 +57,7 @@ classes that do the rote work of constructing all the UI elements. @@ -57,7 +57,7 @@ classes that do the rote work of constructing all the UI elements.
wxWidgets
---------
DOS shell:
cd \wxWidgets-2.9.1-mgw\build\msw
cd \wxWidgets-2.9.2-mgw\build\msw
mingw32-make -f makefile.gcc
OpenSSL
@ -73,30 +73,26 @@ make @@ -73,30 +73,26 @@ make
Berkeley DB
-----------
MSYS shell:
cd /c/db-4.7.25.NC-mgw/build_unix
cd /c/db-4.8.30.NC-mgw/build_unix
sh ../dist/configure --enable-mingw --enable-cxx
make
Boost
-----
DOS prompt:
downloaded boost jam 3.1.18
cd \boost-1.43.0-mgw
cd \boost-1.47.0-mgw
bjam toolset=gcc --build-type=complete stage
Note:
building with boost 1.45.0 failed because of boost ticket 4614, 4258
builds fine with boost 1.43.0
MiniUPnPc
---------
Building miniupnpc failed on Windows Server 2003, thus it is expected that a binary copy will be used.
See http://miniupnp.tuxfamily.org/forum/viewtopic.php?t=642
UPnP support is optional, make with USE_UPNP= to disable it.
Get upnpc-exe-win32-20110215.zip and unzip it to \upnpc-exe-win32-20110215
Get miniupnpc-1.5.20110215.tar.gz and copy *.h to \upnpc-exe-win32-20110215\miniupnpc
MSYS shell:
cd /c/miniupnpc-1.6-mgw
make -f Makefile.mingw
mkdir miniupnpc
cp *.h miniupnpc/
Bitcoin
-------

18
doc/build-osx.txt

@ -135,18 +135,18 @@ The process for miniupnpc (optional) is similar to that of OpenSSL. @@ -135,18 +135,18 @@ The process for miniupnpc (optional) is similar to that of OpenSSL.
Download from http://miniupnp.tuxfamily.org/files/.
cd ~/bitcoin/deps
tar xvf ~/Downloads/miniupnpc-1.5.tar
mv miniupnpc-1.5 miniupnpc-1.5-x86_64
tar xvf ~/Downloads/miniupnpc-1.5.tar
mv miniupnpc-1.5 miniupnpc-1.5-i386
tar xvf ~/Downloads/miniupnpc-1.6.tar
mv miniupnpc-1.6 miniupnpc-1.6-x86_64
tar xvf ~/Downloads/miniupnpc-1.6.tar
mv miniupnpc-1.6 miniupnpc-1.6-i386
# build x86_64 (64 bit intel) binary
cd miniupnpc-1.5-x86_64
cd miniupnpc-1.6-x86_64
export CFLAGS="-arch x86_64"
export LDFLAGS="-arch x86_64"
export PREFIX="/Users/macuser/bitcoin/deps"
make && make install
# build i386 (32 bit intel) binary
cd miniupnpc-1.5-i386
cd miniupnpc-1.6-i386
export CFLAGS="-arch i386"
export LDFLAGS="-arch i386"
export PREFIX="/Users/macuser/bitcoin/deps"
@ -154,7 +154,7 @@ make @@ -154,7 +154,7 @@ make
# combine the libs
cd ~/bitcoin/deps
lipo -arch i386 miniupnpc-1.5-i386/libminiupnpc.a -arch x86_64 miniupnpc-1.5-x86_64/libminiupnpc.a -o lib/libminiupnpc.a -create
lipo -arch i386 miniupnpc-1.6-i386/libminiupnpc.a -arch x86_64 miniupnpc-1.6-x86_64/libminiupnpc.a -o lib/libminiupnpc.a -create
Verify your binaries
@ -175,8 +175,8 @@ Berkeley DB @@ -175,8 +175,8 @@ Berkeley DB
Download from http://freshmeat.net/projects/berkeleydb/
cd ~/bitcoin/deps
tar xvf ~/Downloads/db-4.8.26.tar
cd db-4.8.26/build_unix
tar xvf ~/Downloads/db-4.8.30.tar
cd db-4.8.30/build_unix
../dist/configure --prefix=/Users/macosuser/bitcoin/deps --enable-cxx && make && make install

21
doc/build-unix.txt

@ -25,8 +25,8 @@ Dependencies @@ -25,8 +25,8 @@ Dependencies
sudo apt-get install build-essential
sudo apt-get install libgtk2.0-dev
sudo apt-get install libssl-dev
sudo apt-get install libdb4.7-dev
sudo apt-get install libdb4.7++-dev
sudo apt-get install libdb4.8-dev
sudo apt-get install libdb4.8++-dev
Boost 1.40+: sudo apt-get install libboost-all-dev
or Boost 1.37: sudo apt-get install libboost1.37-dev
@ -55,10 +55,10 @@ miniupnpc New (3-clause) BSD license @@ -55,10 +55,10 @@ miniupnpc New (3-clause) BSD license
Versions used in this release:
GCC 4.3.3
OpenSSL 0.9.8g
wxWidgets 2.9.0
Berkeley DB 4.7.25.NC
wxWidgets 2.9.2
Berkeley DB 4.8.30.NC
Boost 1.37
miniupnpc 1.5
miniupnpc 1.6
Notes
@ -74,8 +74,8 @@ symbols, which reduces the executable size by about 90%. @@ -74,8 +74,8 @@ symbols, which reduces the executable size by about 90%.
wxWidgets
---------
cd /usr/local
tar -xzvf wxWidgets-2.9.0.tar.gz
cd wxWidgets-2.9.0
tar -xzvf wxWidgets-2.9.2.tar.gz
cd wxWidgets-2.9.2
mkdir buildgtk
cd buildgtk
../configure --with-gtk --enable-debug --disable-shared --enable-monolithic --without-libpng --disable-svg
@ -87,8 +87,8 @@ ldconfig @@ -87,8 +87,8 @@ ldconfig
miniupnpc
---------
tar -xzvf miniupnpc-1.5.tar.gz
cd miniupnpc-1.5
tar -xzvf miniupnpc-1.6.tar.gz
cd miniupnpc-1.6
make
sudo su
make install
@ -96,8 +96,7 @@ make install @@ -96,8 +96,7 @@ make install
Berkeley DB
-----------
You need Berkeley DB 4.7. Don't use 4.8, the database/log0000* files
are incompatible. If you have to build Berkeley DB yourself:
You need Berkeley DB 4.8. If you have to build Berkeley DB yourself:
../dist/configure --enable-cxx
make

44
doc/coding.txt

@ -39,3 +39,47 @@ v vector or similar list objects @@ -39,3 +39,47 @@ v vector or similar list objects
map map or multimap
set set or multiset
bn CBigNum
-------------------------
Locking/mutex usage notes
The code is multi-threaded, and uses mutexes and the CRITICAL_BLOCK/TRY_CRITICAL_BLOCK macros to protect data structures.
Deadlocks due to inconsistent lock ordering (thread 1 locks cs_main and then cs_wallet, while thread 2 locks them in the opposite order: result, deadlock as each waits for the other to release its lock) are a problem. Compile with -DDEBUG_LOCKORDER to get lock order inconsistencies reported in the debug.log file.
Re-architecting the core code so there are better-defined interfaces between the various components is a goal, with any necessary locking done by the components (e.g. see the self-contained CKeyStore class and its cs_KeyStore lock for example).
-------
Threads
StartNode : Starts other threads.
ThreadGetMyExternalIP : Determines outside-the-firewall IP address, sends addr message to connected peers when it determines it.
ThreadIRCSeed : Joins IRC bootstrapping channel, watching for new peers and advertising this node's IP address.
ThreadSocketHandler : Sends/Receives data from peers on port 8333.
ThreadMessageHandler : Higher-level message handling (sending and receiving).
ThreadOpenConnections : Initiates new connections to peers.
ThreadTopUpKeyPool : replenishes the keystore's keypool.
ThreadCleanWalletPassphrase : re-locks an encrypted wallet after user has unlocked it for a period of time.
SendingDialogStartTransfer : used by pay-via-ip-address code (obsolete)
ThreadDelayedRepaint : repaint the gui
ThreadFlushWalletDB : Close the wallet.dat file if it hasn't been used in 500ms.
ThreadRPCServer : Remote procedure call handler, listens on port 8332 for connections and services them.
ThreadBitcoinMiner : Generates bitcoins
ThreadMapPort : Universal plug-and-play startup/shutdown
Shutdown : Does an orderly shutdown of everything
ExitTimeout : Windows-only, sleeps 5 seconds then exits application

636
locale/pl/LC_MESSAGES/bitcoin.po

File diff suppressed because it is too large Load Diff

642
src/bitcoinrpc.cpp

@ -331,71 +331,59 @@ Value getnewaddress(const Array& params, bool fHelp) @@ -331,71 +331,59 @@ Value getnewaddress(const Array& params, bool fHelp)
"If [account] is specified (recommended), it is added to the address book "
"so payments received with the address will be credited to [account].");
if (!pwalletMain->IsLocked())
pwalletMain->TopUpKeyPool();
if (pwalletMain->GetKeyPoolSize() < 1)
throw JSONRPCError(-12, "Error: Keypool ran out, please call keypoolrefill first");
// Parse the account first so we don't generate a key if there's an error
string strAccount;
if (params.size() > 0)
strAccount = AccountFromValue(params[0]);
if (!pwalletMain->IsLocked())
pwalletMain->TopUpKeyPool();
// Generate a new key that is added to wallet
CBitcoinAddress address(pwalletMain->GetOrReuseKeyFromPool());
std::vector<unsigned char> newKey;
if (!pwalletMain->GetKeyFromPool(newKey, false))
throw JSONRPCError(-12, "Error: Keypool ran out, please call keypoolrefill first");
CBitcoinAddress address(newKey);
// This could be done in the same main CS as GetKeyFromKeyPool.
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
pwalletMain->SetAddressBookName(address, strAccount);
pwalletMain->SetAddressBookName(address, strAccount);
return address.ToString();
}
// requires cs_main, cs_mapWallet, cs_mapAddressBook locks
CBitcoinAddress GetAccountAddress(string strAccount, bool bForceNew=false)
{
CWalletDB walletdb(pwalletMain->strWalletFile);
CAccount account;
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
{
walletdb.ReadAccount(strAccount, account);
walletdb.ReadAccount(strAccount, account);
bool bKeyUsed = false;
bool bKeyUsed = false;
// Check if the current key has been used
if (!account.vchPubKey.empty())
// Check if the current key has been used
if (!account.vchPubKey.empty())
{
CScript scriptPubKey;
scriptPubKey.SetBitcoinAddress(account.vchPubKey);
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin();
it != pwalletMain->mapWallet.end() && !account.vchPubKey.empty();
++it)
{
CScript scriptPubKey;
scriptPubKey.SetBitcoinAddress(account.vchPubKey);
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin();
it != pwalletMain->mapWallet.end() && !account.vchPubKey.empty();
++it)
{
const CWalletTx& wtx = (*it).second;
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
if (txout.scriptPubKey == scriptPubKey)
bKeyUsed = true;
}
const CWalletTx& wtx = (*it).second;
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
if (txout.scriptPubKey == scriptPubKey)
bKeyUsed = true;
}
}
// Generate a new key
if (account.vchPubKey.empty() || bForceNew || bKeyUsed)
{
if (pwalletMain->GetKeyPoolSize() < 1)
{
if (bKeyUsed || bForceNew)
throw JSONRPCError(-12, "Error: Keypool ran out, please call topupkeypool first");
}
else
{
account.vchPubKey = pwalletMain->GetOrReuseKeyFromPool();
pwalletMain->SetAddressBookName(CBitcoinAddress(account.vchPubKey), strAccount);
walletdb.WriteAccount(strAccount, account);
}
}
// Generate a new key
if (account.vchPubKey.empty() || bForceNew || bKeyUsed)
{
if (!pwalletMain->GetKeyFromPool(account.vchPubKey, false))
throw JSONRPCError(-12, "Error: Keypool ran out, please call keypoolrefill first");
pwalletMain->SetAddressBookName(CBitcoinAddress(account.vchPubKey), strAccount);
walletdb.WriteAccount(strAccount, account);
}
return CBitcoinAddress(account.vchPubKey);
@ -413,12 +401,7 @@ Value getaccountaddress(const Array& params, bool fHelp) @@ -413,12 +401,7 @@ Value getaccountaddress(const Array& params, bool fHelp)
Value ret;
CRITICAL_BLOCK(cs_main)
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
{
ret = GetAccountAddress(strAccount).ToString();
}
ret = GetAccountAddress(strAccount).ToString();
return ret;
}
@ -442,20 +425,15 @@ Value setaccount(const Array& params, bool fHelp) @@ -442,20 +425,15 @@ Value setaccount(const Array& params, bool fHelp)
strAccount = AccountFromValue(params[1]);
// Detect when changing the account of an address that is the 'unused current key' of another account:
CRITICAL_BLOCK(cs_main)
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
if (pwalletMain->mapAddressBook.count(address))
{
if (pwalletMain->mapAddressBook.count(address))
{
string strOldAccount = pwalletMain->mapAddressBook[address];
if (address == GetAccountAddress(strOldAccount))
GetAccountAddress(strOldAccount, true);
}
pwalletMain->SetAddressBookName(address, strAccount);
string strOldAccount = pwalletMain->mapAddressBook[address];
if (address == GetAccountAddress(strOldAccount))
GetAccountAddress(strOldAccount, true);
}
pwalletMain->SetAddressBookName(address, strAccount);
return Value::null;
}
@ -472,12 +450,9 @@ Value getaccount(const Array& params, bool fHelp) @@ -472,12 +450,9 @@ Value getaccount(const Array& params, bool fHelp)
throw JSONRPCError(-5, "Invalid bitcoin address");
string strAccount;
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
{
map<CBitcoinAddress, string>::iterator mi = pwalletMain->mapAddressBook.find(address);
if (mi != pwalletMain->mapAddressBook.end() && !(*mi).second.empty())
strAccount = (*mi).second;
}
map<CBitcoinAddress, string>::iterator mi = pwalletMain->mapAddressBook.find(address);
if (mi != pwalletMain->mapAddressBook.end() && !(*mi).second.empty())
strAccount = (*mi).second;
return strAccount;
}
@ -493,15 +468,12 @@ Value getaddressesbyaccount(const Array& params, bool fHelp) @@ -493,15 +468,12 @@ Value getaddressesbyaccount(const Array& params, bool fHelp)
// Find all addresses that have the given account
Array ret;
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
BOOST_FOREACH(const PAIRTYPE(CBitcoinAddress, string)& item, pwalletMain->mapAddressBook)
{
BOOST_FOREACH(const PAIRTYPE(CBitcoinAddress, string)& item, pwalletMain->mapAddressBook)
{
const CBitcoinAddress& address = item.first;
const string& strName = item.second;
if (strName == strAccount)
ret.push_back(address.ToString());
}
const CBitcoinAddress& address = item.first;
const string& strName = item.second;
if (strName == strAccount)
ret.push_back(address.ToString());
}
return ret;
}
@ -548,16 +520,12 @@ Value sendtoaddress(const Array& params, bool fHelp) @@ -548,16 +520,12 @@ Value sendtoaddress(const Array& params, bool fHelp)
if (params.size() > 3 && params[3].type() != null_type && !params[3].get_str().empty())
wtx.mapValue["to"] = params[3].get_str();
CRITICAL_BLOCK(cs_main)
CRITICAL_BLOCK(pwalletMain->cs_vMasterKey)
{
if(pwalletMain->IsLocked())
throw JSONRPCError(-14, "Error: The wallet passphrase entered was incorrect.");
if (pwalletMain->IsLocked())
throw JSONRPCError(-13, "Error: Please enter the wallet passphrase with walletpassphrase first.");
string strError = pwalletMain->SendMoneyToBitcoinAddress(address, nAmount, wtx);
if (strError != "")
throw JSONRPCError(-4, strError);
}
string strError = pwalletMain->SendMoneyToBitcoinAddress(address, nAmount, wtx);
if (strError != "")
throw JSONRPCError(-4, strError);
return wtx.GetHash().GetHex();
}
@ -586,19 +554,16 @@ Value getreceivedbyaddress(const Array& params, bool fHelp) @@ -586,19 +554,16 @@ Value getreceivedbyaddress(const Array& params, bool fHelp)
// Tally
int64 nAmount = 0;
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
const CWalletTx& wtx = (*it).second;
if (wtx.IsCoinBase() || !wtx.IsFinal())
continue;
const CWalletTx& wtx = (*it).second;
if (wtx.IsCoinBase() || !wtx.IsFinal())
continue;
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
if (txout.scriptPubKey == scriptPubKey)
if (wtx.GetDepthInMainChain() >= nMinDepth)
nAmount += txout.nValue;
}
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
if (txout.scriptPubKey == scriptPubKey)
if (wtx.GetDepthInMainChain() >= nMinDepth)
nAmount += txout.nValue;
}
return ValueFromAmount(nAmount);
@ -607,15 +572,12 @@ Value getreceivedbyaddress(const Array& params, bool fHelp) @@ -607,15 +572,12 @@ Value getreceivedbyaddress(const Array& params, bool fHelp)
void GetAccountAddresses(string strAccount, set<CBitcoinAddress>& setAddress)
{
CRITICAL_BLOCK(pwalletMain->cs_mapAddressBook)
BOOST_FOREACH(const PAIRTYPE(CBitcoinAddress, string)& item, pwalletMain->mapAddressBook)
{
BOOST_FOREACH(const PAIRTYPE(CBitcoinAddress, string)& item, pwalletMain->mapAddressBook)
{
const CBitcoinAddress& address = item.first;
const string& strName = item.second;
if (strName == strAccount)
setAddress.insert(address);
}
const CBitcoinAddress& address = item.first;
const string& strName = item.second;
if (strName == strAccount)
setAddress.insert(address);
}
}
@ -639,21 +601,18 @@ Value getreceivedbyaccount(const Array& params, bool fHelp) @@ -639,21 +601,18 @@ Value getreceivedbyaccount(const Array& params, bool fHelp)
// Tally
int64 nAmount = 0;
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
const CWalletTx& wtx = (*it).second;
if (wtx.IsCoinBase() || !wtx.IsFinal())
continue;
const CWalletTx& wtx = (*it).second;
if (wtx.IsCoinBase() || !wtx.IsFinal())
continue;
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
{
CBitcoinAddress address;
if (ExtractAddress(txout.scriptPubKey, pwalletMain, address) && setAddress.count(address))
if (wtx.GetDepthInMainChain() >= nMinDepth)
nAmount += txout.nValue;
}
BOOST_FOREACH(const CTxOut& txout, wtx.vout)
{
CBitcoinAddress address;
if (ExtractAddress(txout.scriptPubKey, pwalletMain, address) && setAddress.count(address))
if (wtx.GetDepthInMainChain() >= nMinDepth)
nAmount += txout.nValue;
}
}
@ -664,27 +623,25 @@ Value getreceivedbyaccount(const Array& params, bool fHelp) @@ -664,27 +623,25 @@ Value getreceivedbyaccount(const Array& params, bool fHelp)
int64 GetAccountBalance(CWalletDB& walletdb, const string& strAccount, int nMinDepth)
{
int64 nBalance = 0;
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
{
// Tally wallet transactions
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
const CWalletTx& wtx = (*it).second;
if (!wtx.IsFinal())
continue;
int64 nGenerated, nReceived, nSent, nFee;
wtx.GetAccountAmounts(strAccount, nGenerated, nReceived, nSent, nFee);
// Tally wallet transactions
for (map<uint256, CWalletTx>::iterator it = pwalletMain->mapWallet.begin(); it != pwalletMain->mapWallet.end(); ++it)
{
const CWalletTx& wtx = (*it).second;
if (!wtx.IsFinal())
continue;
if (nReceived != 0 && wtx.GetDepthInMainChain() >= nMinDepth)
nBalance += nReceived;
nBalance += nGenerated - nSent - nFee;
}
int64 nGenerated, nReceived, nSent, nFee;
wtx.GetAccountAmounts(strAccount, nGenerated, nReceived, nSent, nFee);
// Tally internal accounting entries
nBalance += walletdb.GetAccountCreditDebit(strAccount);
if (nReceived != 0 && wtx.GetDepthInMainChain() >= nMinDepth)
nBalance += nReceived;
nBalance += nGenerated - nSent - nFee;
}
// Tally internal accounting entries
nBalance += walletdb.GetAccountCreditDebit(strAccount);
return nBalance;
}
@ -763,33 +720,31 @@ Value movecmd(const Array& params, bool fHelp) @@ -763,33 +720,31 @@ Value movecmd(const Array& params, bool fHelp)
if (params.size() > 4)
strComment = params[4].get_str();
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
{
CWalletDB walletdb(pwalletMain->strWalletFile);
walletdb.TxnBegin();
int64 nNow = GetAdjustedTime();
// Debit
CAccountingEntry debit;
debit.strAccount = strFrom;
debit.nCreditDebit = -nAmount;
debit.nTime = nNow;
debit.strOtherAccount = strTo;
debit.strComment = strComment;
walletdb.WriteAccountingEntry(debit);
// Credit
CAccountingEntry credit;
credit.strAccount = strTo;
credit.nCreditDebit = nAmount;
credit.nTime = nNow;
credit.strOtherAccount = strFrom;
credit.strComment = strComment;
walletdb.WriteAccountingEntry(credit);
walletdb.TxnCommit();
}
CWalletDB walletdb(pwalletMain->strWalletFile);
walletdb.TxnBegin();
int64 nNow = GetAdjustedTime();
// Debit
CAccountingEntry debit;
debit.strAccount = strFrom;
debit.nCreditDebit = -nAmount;
debit.nTime = nNow;
debit.strOtherAccount = strTo;
debit.strComment = strComment;
walletdb.WriteAccountingEntry(debit);
// Credit
CAccountingEntry credit;
credit.strAccount = strTo;
credit.nCreditDebit = nAmount;
credit.nTime = nNow;
credit.strOtherAccount = strFrom;
credit.strComment = strComment;
walletdb.WriteAccountingEntry(credit);
walletdb.TxnCommit();
return true;
}
@ -822,23 +777,18 @@ Value sendfrom(const Array& params, bool fHelp) @@ -822,23 +777,18 @@ Value sendfrom(const Array& params, bool fHelp)
if (params.size() > 5 && params[5].type() != null_type && !params[5].get_str().empty())
wtx.mapValue["to"] = params[5].get_str();
CRITICAL_BLOCK(cs_main)
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
CRITICAL_BLOCK(pwalletMain->cs_vMasterKey)
{
if(pwalletMain->IsLocked())
throw JSONRPCError(-14, "Error: The wallet passphrase entered was incorrect.");
if (pwalletMain->IsLocked())
throw JSONRPCError(-13, "Error: Please enter the wallet passphrase with walletpassphrase first.");
// Check funds
int64 nBalance = GetAccountBalance(strAccount, nMinDepth);
if (nAmount > nBalance)
throw JSONRPCError(-6, "Account has insufficient funds");
// Check funds
int64 nBalance = GetAccountBalance(strAccount, nMinDepth);
if (nAmount > nBalance)
throw JSONRPCError(-6, "Account has insufficient funds");
// Send
string strError = pwalletMain->SendMoneyToBitcoinAddress(address, nAmount, wtx);
if (strError != "")
throw JSONRPCError(-4, strError);
}
// Send
string strError = pwalletMain->SendMoneyToBitcoinAddress(address, nAmount, wtx);
if (strError != "")
throw JSONRPCError(-4, strError);
return wtx.GetHash().GetHex();
}
@ -889,31 +839,26 @@ Value sendmany(const Array& params, bool fHelp) @@ -889,31 +839,26 @@ Value sendmany(const Array& params, bool fHelp)
vecSend.push_back(make_pair(scriptPubKey, nAmount));
}
CRITICAL_BLOCK(cs_main)
CRITICAL_BLOCK(pwalletMain->cs_mapWallet)
CRITICAL_BLOCK(pwalletMain->cs_vMasterKey)
{
if(pwalletMain->IsLocked())
throw JSONRPCError(-14, "Error: The wallet passphrase entered was incorrect.");
// Check funds
int64 nBalance = GetAccountBalance(strAccount, nMinDepth);
if (totalAmount > nBalance)
throw JSONRPCError(-6, "Account has insufficient funds");
if (pwalletMain->IsLocked())
throw JSONRPCError(-13, "Error: Please enter the wallet passphrase with walletpassphrase first.");
// Send
CReserveKey keyChange(pwalletMain);
int64 nFeeRequired = 0;
bool fCreated = pwalletMain->CreateTransaction(vecSend, wtx, keyChange, nFeeRequired);