Browse Source

Test UTF-8 passwords; add release notes

MMGen 6 years ago
parent
commit
6972153248

+ 0 - 10
doc/README.mswin

@@ -1,10 +0,0 @@
-MMGen MS Windows Notes
-
-The following MMGen features are unsupported or broken on the MSWin/MinGW platform:
-
-- Autosign (not supported)
-- Zcash z-address generation (requires libsodium)
-- Monero wallet creation/syncing* (IO stream issues with pexpect and the password prompt)
-- UTF-8 label, filename and path support (may work on versions of Windows with native UTF-8 support)
-
-*Monero address and viewkey generation works fine.

+ 10 - 0
doc/README.mswin.md

@@ -0,0 +1,10 @@
+### MMGen MS Windows Notes
+
+The following MMGen features are unsupported or broken on the MSWin/MinGW platform:
+
+- Autosign (not supported)
+- Zcash z-address generation (requires libsodium)
+- Monero wallet creation/syncing\* (IO stream issues with pexpect and the password prompt)
+- UTF-8 filename and path support
+
+\*Monero address and viewkey generation are fully supported.

+ 23 - 0
doc/release-notes/release-notes-v0.8.3.md

@@ -0,0 +1,23 @@
+MMGen version 0.8.3
+
+New features/improvements:
+
+	* New native Bitcoin RPC library.
+	* Support for cookie-based RPC authentication (new in Bitcoin Core v0.12.0).
+	* Batch mode available when listing and importing addresses.
+	* mmgen-tool listaddresses: 'addrs' argument allows you to specify an
+	  address or range of addresses.
+
+NOTE: if MMGen is already installed on your system, you must remove your
+existing installation by hand before installing this new version.  On Linux,
+this means deleting everything under the directory
+'/usr/local/lib/python2.7/dist-packages/mmgen/'.  Also, if you did a 'git pull'
+instead of a fresh clone, you must delete the 'build' directory in the
+repository root before installing.
+
+The 'mmgen-pywallet' utility has been removed.  It's no longer needed, as the
+'bitcoin-cli dumpwallet' command (available since Core v0.9.0) provides
+equivalent functionality.
+
+The Windows port isn't being actively maintained at the moment.  Use at your own
+risk, and report any problems on the Bitcointalk forum.

+ 16 - 0
doc/release-notes/release-notes-v0.8.5.md

@@ -0,0 +1,16 @@
+MMGen version 0.8.5
+
+New features/improvements:
+
+	* Colored output
+	* Label editing in mmgen-txcreate
+
+This release includes a major object-oriented rewrite of much of the code.
+
+NOTE: The transaction file format has changed.  Since TX files are temporary, this
+shouldn't be a problem for most.  However, the script 'tx-old2new.py' in the
+scripts directory will convert old old TX files to the new format for those who
+need to do so.
+
+The Windows implementation is functional again.  Use at your own risk, and
+report any problems on the Bitcointalk forum.

+ 7 - 0
doc/release-notes/release-notes-v0.8.6.md

@@ -0,0 +1,7 @@
+**New features/improvements**
+
+- Address generation using secp256k1 library (Linux only)
+
+Instructions for installing the secp256k1 library on your system can be found at doc/wiki/install-linux/Install-MMGen-on-Debian-or-Ubuntu-Linux.md
+
+If secp256k1 is not installed on the system, MMGen will still be usable. It just falls back to 'keyconv', or failing that, python-ecdsa for generating addresses.

+ 12 - 0
doc/release-notes/release-notes-v0.8.7.md

@@ -0,0 +1,12 @@
+*Assorted fixes/improvements*
+
+- Importing addresses with `--rescan` working again
+- Tracking and spending non-MMGen addresses now fully functional
+- `mmgen-txcreate`: improvements in unspent outputs display
+- `mmgen-txsign`: use bitcoind wallet dump as keylist fixed
+
+- Testnet support:
+  - Practice sending transactions without risking funds
+	(free testnet coins: https://tpfaucet.appspot.com/)
+  - Test suite fully supported
+  - To enable, set `MMGEN_TESTNET` environment variable

+ 12 - 0
doc/release-notes/release-notes-v0.8.7pre.md

@@ -0,0 +1,12 @@
+Assorted fixes/improvements:
+
+- Importing addresses with --rescan working again
+- Tracking and spending non-MMGen addresses fully functional
+- mmgen-txcreate: improvements in unspent outputs display
+- mmgen-txsign: use bitcoind wallet dump as keylist without modification
+
+- Testnet support:
+  - Practice sending transactions without risking real funds
+  	(free testnet coins: https://tpfaucet.appspot.com/)
+  - Test suite fully supported
+  - To enable, set MMGEN_TESTNET environment variable

+ 20 - 0
doc/release-notes/release-notes-v0.8.8.md

@@ -0,0 +1,20 @@
+**Data directory, config file and default wallet support**
+- Data directory is `~/.mmgen`; config file is `mmgen.cfg`.
+- When default wallet is present in data directory, specifying the wallet
+  on the command line is optional.
+- Datadir structure mirrors that of Bitcoin Core: mainnet and testnet share
+  a common config file, with testnet putting its own files, including the
+  default wallet, in the subdirectory 'testnet3'.
+- Global vars are now overriden in this order:
+  1) config file
+  2) environmental variables beginning with `MMGEN_` (listed in globalvars.py)
+  3) command line
+- Long (common) opts added for setting global vars; display with `--longhelp`.
+
+The test suite has been updated to test these new features.
+
+**Other changes**
+- Always get user entropy, even for non-critical randomness, unless `-r0`.
+- rpcuser,rpcpassword now override cookie authentication, as with Core.
+- Communication with remote bitcoind supported with `--rpc-host` option.
+- Testnet use can be overridden with the `--testnet=0|1` option.

+ 15 - 0
doc/release-notes/release-notes-v0.8.9.md

@@ -0,0 +1,15 @@
+This release brings full functionality and wider testing to the MS Windows port. MMGen now works with both WinXP/MinGW32 and Win7+/MinGW64, and separate, updated installation instructions for both platforms have been added to the wiki. A working MinGW environment is now required to run MMGen.
+
+New Windows features:
+- Full non-interactive test suite support with pexpect (PopenSpawn)
+- secp256k1 address generation support
+- Secure wallet deletion with sdelete
+
+Windows bugfixes:
+- A critical bug in writing the encrypted keyaddrfile has been fixed. This bug
+  would have affected only online wallet use and would not have led to the loss
+  of coins
+- Cookie filename fixed; RPC cookie authentication now functional
+
+General features:
+- --bitcoin-data-dir, --rpc-port, --rpc-user, and --rpc-password options

+ 11 - 0
doc/release-notes/release-notes-v0.9.0.md

@@ -0,0 +1,11 @@
+New features:
+- New `mmgen-txdo` command creates, signs and sends transactions in one operation
+- Exporting seed to hexadecimal (mmhex) format now supported
+- Support for 8-color terminals, better default colors on 256-color terminals
+- `--force-256-color` option overrides terminfo entry and $TERM environment variable
+- Selected commands of `mmgen-tool` now accept stdin input
+- Transaction file format change: TXID appended to file after tx is broadcast
+
+A new tutorial, [Recovering Keys Without MMGen][01], has been added to the wiki
+
+[01]: https://github.com/mmgen/mmgen/wiki/Recovering-Keys-Without-MMGen

+ 25 - 0
doc/release-notes/release-notes-v0.9.1.md

@@ -0,0 +1,25 @@
+BIP 125 replace-by-fee (RBF) support:
+- Create replaceable transactions using the `--rbf` switch to `mmgen-txcreate` and `mmgen-txdo`
+- Create, and optionally sign and send, replacement transactions with the new `mmgen-txbump` command
+
+Satoshis-per-byte format:
+- Tx fees, both on the command line and at the interactive prompt, may be specified either as absolute BTC amounts or in satoshis-per-byte format (an integer followed by the letter 's')
+
+Improved fee handling:
+- Completely reworked fee-handling code with better fee checking
+- default tx fee eliminated, max_tx_fee configurable in mmgen.cfg
+
+Command scriptability:
+- New `--yes` switch makes `mmgen-txbump` and `mmgen-txsign` fully non-interactive and `mmgen-txcreate` and `mmgen-txsend` mostly non-interactive
+
+Bugfixes and usability improvements:
+- 'mmgen-tool listaddresses' now list addresses from multiple seeds correctly
+- Improved user interaction with all 'mmgen-tx*' commands
+
+The RBF and new fee functionality are documented in the [Getting Started][01] guide.
+
+The guide has also been updated with a new [Preliminaries][03] section and a new [Hot wallets and key-address files][02] section.
+
+[01]: https://github.com/mmgen/mmgen/wiki/Getting-Started-with-MMGen#a_fee
+[02]: https://github.com/mmgen/mmgen/wiki/Getting-Started-with-MMGen#a_hw
+[03]: https://github.com/mmgen/mmgen/wiki/Getting-Started-with-MMGen#a_i

+ 12 - 0
doc/release-notes/release-notes-v0.9.3.md

@@ -0,0 +1,12 @@
+**New features:**
+
+- Bob and Alice regtest mode for testing MMGen in a mock two-user environment.
+  [Documented](https://github.com/mmgen/mmgen/wiki/MMGen-Quick-Start-with-Regtest-Mode) in the wiki, tests added to test suite
+
+  - Compressed P2PKH address support (address type 'C')
+
+  - BCH (Bitcoin Cash) support
+
+  - Segwit (address type 'S') support deployed after Segwit activation on mainnet
+
+  - and, of course, numerous bugfixes and small improvements

+ 8 - 0
doc/release-notes/release-notes-v0.9.5.md

@@ -0,0 +1,8 @@
+URL: https://github.com/mmgen/mmgen/releases/tag/v0.9.5
+
+**New features:**
+
+  - Altcoin framework + full Litecoin support [(commit)](https://github.com/mmgen/mmgen/commit/35d10911596c76227b8cd6318681c6ac9dc02a42)
+
+  - Offline transaction autosigning [(commit)](https://github.com/mmgen/mmgen/commit/8fb3efd99cc2f62e7f12f0e1f9893dd287064035) [(VIDEO)](https://github.com/mmgen/mmgen/releases/tag/autosign)
+

+ 8 - 0
doc/release-notes/release-notes-v0.9.6.md

@@ -0,0 +1,8 @@
+**New features:**
+
+  - Key/address generation support for ETH, ETC, ZEC, XMR and 144 Bitcoin-derived altcoins
+  - Zcash z-address support (Linux only)
+  - Monero wallet generation utility (Linux only): `mmgen-tool keyaddrlist2monerowallet`
+  - 32-byte hexadecimal password generation with `mmgen-passgen --hex`
+
+  Altcoin support is EXPERIMENTAL. Use at your own risk

+ 6 - 0
doc/release-notes/release-notes-v0.9.7.md

@@ -0,0 +1,6 @@
+**New features:**
+
+  - Monero wallet syncing utility (258651a)
+  - mmgen-tool listaddresses: add 'show_age','show_days' options (f7e54cc)
+
+This release closes a serious exploit (6b9df0e). Upgrading is advised. In particular, the **offline** MMGen installation in an online/offline setup should be upgraded.

+ 46 - 0
doc/release-notes/release-notes-v0.9.8.md

@@ -0,0 +1,46 @@
+### MMGen Version 0.9.8 Release Notes
+
+**Interesting new features:**
+
+  - Bech32 address support (BTC: e4114ee, LTC: 2cb4df7)
+  - Stealth mnemonic entry (90ebc94)
+
+**New comprehensive UTF-8 support:**
+
+  - UTF-8 filenames and paths (896c7fe)
+  - UTF-8 tracking wallet comments (d49c862)
+  - UTF-8 wallet labels (2104273)
+  - Proper formatting of CJK strings (ea6629d)
+
+**Security/bugfixes:**
+
+  - `max_tx_file_size` and other TX file checks (cf20311)
+  - TX size estimation fixes (ed2b94c)
+  - Require brainwallet and passwords to be UTF-8 encoded (9f2153c)
+
+Coin daemons used for testing:
+
+  - Bitcoin Core v0.16.0
+  - Litecoin Core v0.16.0rc1
+  - Bitcoin-ABC v0.17.1
+  - Monero v0.12.0.0 (Lithium Luna)
+
+Tools used for testing:
+
+  - Zcash-Mini (a2b3504)
+  - Pycoin v0.90a
+  - Pyethereum v2.1.2
+  - Vanitygen-Plus (5ca3d22)
+
+Note that some features, notably UTF-8 filename and path support, do not work
+on the MS Windows/MinGW platform.  See the file [doc/README.mswin.md][1] for
+details.
+
+All user input is now required to be UTF-8 encoded.  This will break backward
+compatibility in the unlikely event that a) you're using a non-ASCII wallet
+password or brainwallet, and b) your native charset is non-UTF-8.  If this is
+the case, you must change your wallet password to an ASCII one (or export your
+brainwallet to another MMGen wallet format) using an older version of MMGen
+before upgrading.
+
+[1]: ../doc/README.mswin

+ 1 - 1
mmgen/seed.py

@@ -304,7 +304,7 @@ an empty passphrase, just hit ENTER twice.
 			for i in range(g.passwd_max_tries):
 				pw = ' '.join(get_words_from_user('Enter {}: '.format(desc)))
 				pw2 = ' '.join(get_words_from_user('Repeat passphrase: '))
-				dmsg('Passphrases: [{}] [{}]'.format(pw,pw2))
+				dmsg(u'Passphrases: [{}] [{}]'.format(pw,pw2))
 				if pw == pw2:
 					vmsg('Passphrases match'); break
 				else: msg('Passphrases do not match.  Try again.')

+ 5 - 0
mmgen/test.py

@@ -42,6 +42,11 @@ def cleandir(d):
 
 def getrandnum(n): return int(hexlify(os.urandom(n)),16)
 def getrandhex(n): return hexlify(os.urandom(n))
+def getrandnum_range(nbytes,rn_max):
+	while True:
+		rn = int(hexlify(os.urandom(nbytes)),16)
+		if rn < rn_max: return rn
+
 def getrandstr(num_chars,no_space=False):
 	n,m = 95,32
 	if no_space: n,m = 94,33

+ 3 - 3
mmgen/tw.py

@@ -328,9 +328,9 @@ Display options: show [D]ays, [g]roup, show [m]mgen addr, r[e]draw screen
 
 		try:
 			if not is_mmgen_id(arg1):
-				assert coinaddr,"Invalid coin address for this chain: {}".format(arg1)
-			assert coinaddr,"{pn} address '{ma}' not found in tracking wallet"
-			assert coinaddr.is_in_tracking_wallet(),"Address '{ca}' not found in tracking wallet"
+				assert coinaddr,u"Invalid coin address for this chain: {}".format(arg1)
+			assert coinaddr,u"{pn} address '{ma}' not found in tracking wallet"
+			assert coinaddr.is_in_tracking_wallet(),u"Address '{ca}' not found in tracking wallet"
 		except Exception as e:
 			msg(e[0].format(pn=g.proj_name,ma=mmaddr,ca=coinaddr))
 			return False

+ 1 - 1
mmgen/util.py

@@ -629,7 +629,7 @@ def get_words_from_file(infile,desc,silent=False):
 	try: words = f.read().decode('utf8').split() # split() also strips
 	except: die(1,'{} data must be UTF-8 encoded.'.format(capfirst(desc)))
 	f.close()
-	dmsg('Sanitized input: [{}]'.format(' '.join(words)))
+	dmsg(u'Sanitized input: [{}]'.format(' '.join(words)))
 	return words
 
 def get_words(infile,desc,prompt):

+ 5 - 6
scripts/test-release.sh

@@ -72,7 +72,11 @@ done
 
 shift $((OPTIND-1))
 
-RED="\e[31;1m" GREEN="\e[32;1m" YELLOW="\e[33;1m" RESET="\e[0m"
+REFDIR='test/ref'
+if uname -a | grep -qi mingw; then SUDO='' MINGW=1; else SUDO='sudo' MINGW=''; fi
+[ "$MINGW" ] || RED="\e[31;1m" GREEN="\e[32;1m" YELLOW="\e[33;1m" RESET="\e[0m"
+
+set -e
 
 [ "$NO_INSTALL" ] || {
 	BRANCH=$1; shift
@@ -81,11 +85,6 @@ RED="\e[31;1m" GREEN="\e[32;1m" YELLOW="\e[33;1m" RESET="\e[0m"
 	[ "$FOUND_BRANCH" ] || { echo "Branch '$BRANCH' not found!"; exit; }
 }
 
-set -e
-
-REFDIR=test/ref
-if uname -a | grep -qi mingw; then SUDO='' MINGW=1; else SUDO='sudo' MINGW=''; fi
-
 check() {
 	[ "$BRANCH" ] || { echo 'No branch specified.  Exiting'; exit; }
 	[ "$(git diff $BRANCH)" == "" ] || {

+ 3 - 0
test/mmgen_pexpect.py

@@ -147,6 +147,9 @@ class MMGenPexpect(object):
 				cmd_str = g.traceback_cmd + ' ' + cmd_str
 #			Msg('\ncmd_str: {}'.format(cmd_str))
 			if opt.popen_spawn:
+				# PopenSpawn() requires cmd string to be bytes.  However, it autoconverts unicode
+				# input to bytes, though this behavior seems to be undocumented.  Setting 'encoding'
+				# to 'UTF-8' will cause pexpect to reject non-unicode string input.
 				self.p = PopenSpawn(cmd_str.encode('utf8'))
 			else:
 				self.p = pexpect.spawn(cmd,args)

+ 29 - 29
test/test.py

@@ -49,6 +49,7 @@ pwfile = u'passwd_file'
 
 ref_dir = os.path.join(u'test',u'ref')
 
+rt_pw = u'abc-α'
 ref_wallet_brainpass = 'abc'
 ref_wallet_hash_preset = '1'
 ref_wallet_incog_offset = 123
@@ -164,7 +165,7 @@ altcoin_pfx = '' if g.proto.base_coin == 'BTC' else '-'+g.proto.base_coin
 tn_ext = ('','.testnet')[g.testnet]
 
 coin_sel = g.coin.lower()
-if g.coin == 'B2X': coin_sel = 'btc'
+# if g.coin == 'B2X': coin_sel = 'btc'
 
 fork       = {'bch':'btc','btc':'btc','ltc':'ltc'}[coin_sel]
 tx_fee     = {'btc':'0.0001','bch':'0.001','ltc':'0.01'}[coin_sel]
@@ -207,7 +208,7 @@ def restore_debug():
 cfgs = {
 	'15': {
 		'tmpdir':        os.path.join(u'test',u'tmp15'),
-		'wpasswd':       'Dorian',
+		'wpasswd':       'Dorian',
 		'kapasswd':      'Grok the blockchain',
 		'addr_idx_list': '12,99,5-10,5,12', # 8 addresses
 		'dep_generators':  {
@@ -231,10 +232,10 @@ cfgs = {
 	},
 	'17': { 'tmpdir': os.path.join(u'test',u'tmp17') },
 	'18': { 'tmpdir': os.path.join(u'test',u'tmp18') },
-	'19': { 'tmpdir': os.path.join(u'test',u'tmp19'), 'wpasswd':'abc' },
+#	'19': { 'tmpdir': os.path.join(u'test',u'tmp19'), 'wpasswd':'abc' }, B2X
 	'1': {
 		'tmpdir':        os.path.join(u'test',u'tmp1'),
-		'wpasswd':       'Dorian',
+		'wpasswd':       u'Dorian',
 		'kapasswd':      'Grok the blockchain',
 		'addr_idx_list': '12,99,5-10,5,12', # 8 addresses
 		'dep_generators':  {
@@ -339,7 +340,7 @@ cfgs = {
 	},
 	'5': {
 		'tmpdir':        os.path.join(u'test',u'tmp5'),
-		'wpasswd':       'My changed password',
+		'wpasswd':       'My changed password',
 		'hash_preset':   '2',
 		'dep_generators': {
 			'mmdat':       'passchg',
@@ -1180,7 +1181,7 @@ def write_fake_data_to_file(d):
 	if opt.print_cmdline: msg(bwd_msg)
 	if opt.log: log_fd.write(bwd_msg + ' ')
 	if opt.verbose or opt.exact_output:
-		sys.stderr.write(u"Fake transaction wallet data written to file '{}'\n".format(unspent_data_file))
+		sys.stderr.write(u"Fake transaction wallet data written to file {!r}\n".format(unspent_data_file))
 
 def create_tx_data(sources):
 	tx_data,ad = {},AddrData()
@@ -1241,24 +1242,23 @@ def add_comments_to_addr_file(addrfile,outfile,use_labels=False):
 
 # 100 words chosen randomly from here:
 #   https://github.com/bitcoin/bips/pull/432/files/6332230d63149a950d05db78964a03bfd344e6b0
-rwords = [
-	'ампула','арест','арка','архив','атлас','афера','багаж','башмак','бежать','бидон','брюки','вена',
-	'взвод','виски','волна','вспышка','встреча','гавань','гамма','гора','горшок','депутат','динамика',
-	'доверие','доза','документ','жених','жюри','зависть','заслуга','зато','зацепка','заявка','здание',
-	'зеркало','зефир','зрачок','изнутри','исход','кедр','киоск','кирпич','комната','концерт','косой',
-	'кубок','лачуга','лужа','мелодия','металл','механизм','механизм','механизм','мост','мощность','мыло',
-	'некий','нижний','новый','няня','овощ','ограда','опыт','орел','падение','петля','пила','поцелуй',
-	'пощечина','проект','путем','пыль','роман','рюкзак','сауна','сбыт','север','сейчас','сержант','след',
-	'слуга','снижение','сокол','соус','стакан','статус','сущность','табак','тело','тень','техника','ужин',
-	'упор','уровень','фирма','франция','фуражка','чучело','шрифт','элемент']
-
+rwords = """
+	алфавит алый амнезия амфора артист баян белый биатлон брат бульвар веревка вернуть весть возраст
+	восток горло горный десяток дятел ежевика жест жизнь жрать заговор здание зона изделие итог кабина
+	кавалер каждый канал керосин класс клятва князь кривой крыша крючок кузнец кукла ландшафт мальчик
+	масса масштаб матрос мрак муравей мычать негодяй носок ночной нрав оборот оружие открытие оттенок
+	палуба пароход период пехота печать письмо позор полтора понятие поцелуй почему приступ пруд пятно
+	ранее режим речь роса рынок рябой седой сердце сквозь смех снимок сойти соперник спичка стон
+	сувенир сугроб суть сцена театр тираж толк удивить улыбка фирма читатель эстония эстрада юность
+	"""
 def make_brainwallet_file(fn):
 	# Print random words with random whitespace in between
+	wl = rwords.split()
 	nwords,ws_list,max_spaces = 10,'    \n',5
 	def rand_ws_seq():
 		nchars = getrandnum(1) % max_spaces + 1
-		return ''.join([ws_list[getrandnum(1)%len(ws_list)] for i in range(nchars)])
-	rand_pairs = [rwords[getrandnum(4) % len(rwords)] + rand_ws_seq() for i in range(nwords)]
+		return ''.join([ws_list[getrandnum_range(1,200)%len(ws_list)] for i in range(nchars)])
+	rand_pairs = [wl[getrandnum(1) % len(wl)] + rand_ws_seq() for i in range(nwords)]
 	d = ''.join(rand_pairs).rstrip() + '\n'
 	if opt.verbose: msg_r('Brainwallet password:\n{}'.format(cyan(d)))
 	write_data_to_file(fn,d,'brainwallet password',silent=True)
@@ -2419,7 +2419,7 @@ class MMGenTestSuite(object):
 
 	def regtest_walletgen(self,name,user):
 		t = MMGenExpect(name,'mmgen-walletgen',['-q','-r0','-p1','--'+user])
-		t.passphrase_new('new MMGen wallet','abc')
+		t.passphrase_new('new MMGen wallet',rt_pw)
 		t.label()
 		t.expect('move it to the data directory? (Y/n): ','y')
 		t.written_to_file('MMGen wallet')
@@ -2435,7 +2435,7 @@ class MMGenTestSuite(object):
 	def regtest_user_sid(self,user):
 		return os.path.basename(get_file_with_ext('mmdat',self.regtest_user_dir(user)))[:8]
 
-	def regtest_addrgen(self,name,user,wf=None,passwd='abc',addr_range='1-5'):
+	def regtest_addrgen(self,name,user,wf=None,passwd=rt_pw,addr_range='1-5'):
 		from mmgen.addr import MMGenAddrType
 		for mmtype in g.proto.mmtypes:
 			t = MMGenExpect(name,'mmgen-addrgen',
@@ -2523,7 +2523,7 @@ class MMGenTestSuite(object):
 							outputs_prompt,
 							extra_args=[],
 							wf=None,
-							pw='abc',
+							pw=rt_pw,
 							no_send=False,
 							do_label=False,
 							bad_locktime=False,
@@ -2544,7 +2544,7 @@ class MMGenTestSuite(object):
 		t.expect('OK? (Y/n): ','y') # change OK?
 		t.expect('Add a comment to transaction? (y/N): ',('\n','y')[do_label])
 		if do_label:
-			t.expect('Comment: ',ref_tx_label_jp.encode('utf8')+'\n')
+			t.expect('Comment: ',ref_tx_label_jp+'\n')
 		t.expect('View decoded transaction\? .*?: ',('t','v')[full_tx_view],regex=True)
 		if not do_label: t.expect('to continue: ','\n')
 		t.passphrase('MMGen wallet',pw)
@@ -2608,7 +2608,7 @@ class MMGenTestSuite(object):
 		t.expect('OK? (Y/n): ','y') # output OK?
 		t.expect('OK? (Y/n): ','y') # fee OK?
 		t.expect('Add a comment to transaction? (y/N): ','n')
-		t.passphrase('MMGen wallet','abc')
+		t.passphrase('MMGen wallet',rt_pw)
 		t.written_to_file('Signed transaction')
 		if not no_send:
 			t.expect('to confirm: ','YES, I REALLY WANT TO DO THIS\n')
@@ -2736,11 +2736,11 @@ class MMGenTestSuite(object):
 
 	def regtest_alice_add_label_badaddr(self,name,addr,reply):
 		t = MMGenExpect(name,'mmgen-tool',['--alice','add_label',addr,'(none)'])
-		t.expect(reply,regex=True)
+		t.expect(reply.encode('utf8'),regex=True)
 		t.ok()
 
 	def regtest_alice_add_label_badaddr1(self,name):
-		return self.regtest_alice_add_label_badaddr(name,'abc','Invalid coin address for this chain: abc')
+		return self.regtest_alice_add_label_badaddr(name,rt_pw,u'Invalid coin address for this chain: '+rt_pw)
 
 	def regtest_alice_add_label_badaddr2(self,name):
 		addr = g.proto.pubhash2addr('00'*20,False) # mainnet zero address
@@ -2876,7 +2876,7 @@ class MMGenTestSuite(object):
 		opt.coin = coin
 		sid = self.regtest_user_sid('bob')
 		self.regtest_user_txdo(
-			name,'bob','0.0001',[sid+':S:5'],'1',pw='abc',
+			name,'bob','0.0001',[sid+':S:5'],'1',pw=rt_pw,
 			extra_args=['--locktime='+str(locktime)],
 			bad_locktime=bad_locktime)
 
@@ -2889,7 +2889,7 @@ class MMGenTestSuite(object):
 	def regtest_split_txdo_timelock_good_b2x(self,name):
 		self.regtest_split_txdo_timelock(name,'B2X',locktime=1321009871,bad_locktime=False)
 
-#	def regtest_user_txdo(self,name,user,fee,outputs_cl,outputs_prompt,extra_args=[],wf=None,pw='abc',no_send=False,do_label=False):
+#	def regtest_user_txdo(self,name,user,fee,outputs_cl,outputs_prompt,extra_args=[],wf=None,pw=rt_pw,no_send=False,do_label=False):
 
 	# undocumented admin commands
 	ref_tx_setup = regtest_setup
@@ -2935,7 +2935,7 @@ class MMGenTestSuite(object):
 		t.expect('OK? (Y/n): ','y') # fee OK?
 		t.expect('OK? (Y/n): ','y') # change OK?
 		t.expect('Add a comment to transaction? (y/N): ','y')
-		t.expect('Comment: ',ref_tx_label_zh.encode('utf8')+'\n')
+		t.expect('Comment: ',ref_tx_label_zh+'\n')
 		t.expect('View decoded transaction\? .*?: ','n',regex=True)
 		t.expect('Save transaction? (y/N): ','y')
 		fn = t.written_to_file('Transaction')