Skip to content

andyparkins/additup

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Release Plans

Licensing

The repository for this project is published at github

https://github.com/andyparkins/additup

That, by definition, makes it open source (i.e. you can see the source code). However, while I intend, eventually, to pick a Free Software license for this project, I haven't yet. That means that (if my understanding of copyright law is correct), I still retain copyright to every part of this project.

I'm happy with that as a situation as it stands until the project is more developed, since it means anyone who is interested can view the project, anyone who wanted to contribute can (and would retain their copyright as well), but the code cannot be (legally) taken by someone who is not friendly to free software.

I expect to pick some variant of the GPL when I do pick; but I would like to get advice from the community first (should it ever reach the stage where what license it's under is relevant).

Naming

I needed a name for this project that wasn't "bitcoin" (to avoid confusion); so I picked the first name that came to mind that contained the letters "ADP", my initials.

Donations

1HJDJzxZWDiePYvFKKoR3iKhMu6Z2GLb6T

Donations, should you wish to make any can be sent to the above address (or you can contact me if you would like a private address). Note: your donation will not speed up development (unless you send me a life-changing amount); I work on this because I find it interesting, not for any monetary reward. I am not asking for donations; but I know that people like to show their appreciation; and I do appreciate appreciation.

Grammar

"Bitcoin" is the project; "bitcoins" are the currency. The vagaries of English make this problem easy then for most cases. If the word you are using is plural, it must be 'bitcoins'. If the word you are using is singular and you aren't talking about a currency unit, it must be 'Bitcoin'. The only difficult case then is, "I'm about to send you a bitcoin using the Bitcoin client". I'll try to stick to this convention, and anywhere I don't will be a bug.

Features

Features I'd like to have in my alternative client.

Separation of wallet and block chain

The wallet is a store of public-private key pairs. Nothing more. Transactions shouldn't be "applied" to a wallet. Instead the wallet application should be able to ask the block chain application (or library) what the current balance of any key is.

Human-readable wallet

Storing a wallet in a human-readable file will make humans a lot less scared of it. Berkley DB is uncomfortable to use anyway, it's always changing on-disk format when the version changes. A list of a few thousand keys really doesn't need a database. A couple of ASCII lines per address is manageable without a database.

(See below) my intent is to have one file per key pair. This key pair would be opened for writing only once, upon creation. From then on there would be no need to ever write to the file. This makes them far safer against power failures or crashes than any database will ever be.

In particular, it would be possible to print private keys. (Under the assumption that the user wants to lock that private key in a safe deposit box).

The word "wallet" is wrong

No bitcoins are stored in the wallet. The analogy is therefore flawed and will confuse people. Especially when they find out that a copy of their wallet is just as good as the original. Spending coins using one spends them in the other. Coins are therefore not in the wallet. Rather, proof-of-ownership of particular coins in the block chain is stored in the wallet. The Bitcoin wallet is more like a safe containing deeds of ownership.

This confusion was particularly evident when discussion was going on of a stolen wallet. The victim kept talking about how he was in his room with the door locked at the time of the theft of the coins. Not having understood that once the wallet is copied the theft can take place any time, whenever the robber sees a large amount of coins at one of the stolen addresses. If I got hold of a copy of your wallet in 2010, and in 2015 you suddenly filled it with money -- I could spend that money. The theft happened five years ago, but that won't stop me. One day, this is going to make an interesting case because of statutes of limitations.

Real wallets contain money; Bitcoin wallets don't. "Wallet" is therefore the wrong word.

I don't think I'll get this one passed any of the existing users or developers though. The nomenclature is going to be fixed now, regardless of how confusing it might be for new users.

Multiple, simultaneous wallet support

A wallet shouldn't be a single file, and it shouldn't be necessary to shut down and restart the client simply to look in a different wallet. Instead I'd like to see wallets as directories (or ideally a compressed archive, but that's a bit tougher to do, and potentially riskier).

That directory will contain:

  • The key pairs, with the private key encrypted. I'd like to see these in separate files, one per pair. The reason for this is that it would make it very easy to move a key from one wallet to another; and best of all: doing so wouldn't require any special software. I'd imagine that the PEM format is already set up for this sort of thing.
  • Bookmarks (see below).
  • A key cache. Just like the official client, it's a good idea to keep a list of keys that will be used in the future. This guards against the restoration of an older backup being guaranteed to destroy coins. The older backup is likely to contain the keys that have subsequently been used.
  • Transaction annotations. Transaction IDs are not human friendly. The user is going to want to be able to write "bought a spanner from Bob" against a particular transaction. It might be sensible to keep these annotations in the key pair file.
  • Address annotations. Similarly, the user should be able to label any address.

Shared Wallets

There are many bitcoin web services, mybitcoin, instawallet, exchanges.

All of which take control of your bitcoins.

This is old fashioned thinking though, the idea that my money should be deposited somewhere else before I can use it. There are some advantages (in terms of privacy) to depositing your coins in the web service's wallet; but it's not a requirement.

If we had a client with the above facility: wallets in human readable form, with keys split into private and public parts and stored in separate files, then we could "deposit" private keys with our web service instead of depositing coins. We are no worse off in terms of security: the web service has control of coins that are ours. The difference is this though: we retain control too.

Let's say instawallet used a private key address that I gave it for my online wallet. I retain control of that key. instawallet can use the blockchain to monitor the current balance, it can spend coins when I tell it to just as it can now. One day, instawallet goes down. Not a hack, but a server crash. Because the private key was shared, I can still move those coins.

There is a disadvantage in that moving funds within a web service is no instant, it would have to use the blockchain. There are ways that could be mitigated though; depending on the level of trust the service has in the owner of an address.

Two Factor Authentication

Detection of the presence of a USB key and use of it (or more likely a file on it) as one factor in the encryption needed to get at the private keys in the wallet(s).

It would also be nice to use Google's Authenticator application for two factor authentication, since the app already exists for Android, iPhone and Blackberry.

Google's authenticator is a time based one time password. The application issues a code that changes every 30 seconds. That code is dependent not just on the time, but on a secret that is entered into the phone during two-factor configuration (on Android this can be done with a QR code). A wallet secured in this way would be encrypted using this code and a password.

"Light" modes

There are a number of modes that a Bitcoin node could conceivably operate in:

  • Full block chain. The node downloads every block and every transaction in that block.
  • Block headers only. The node downloads every block header. It cannot perform verification of transactions.
  • Blocks on demand. The node downloads every block header, then, assuming permanent connectivity, when the node needs the transactions from a particular block (say when spending or verifying deposits), it can just ask its peers for it.
  • Block headers on demand. The node downloads nothing. When it needs a particular block header or transaction block it requests it from its peers.

Note in particular that it is the "headers only" mode that is the riskiest. The "on-demand" modes, assuming that the peers are available, still perform whatever verification is necessary, they just do it at their leisure requesting what they need.

Block explorer built in

The block explorer website is an excellent tool. However, it's not acceptable to rely on a web site that uses a special, custom-build of the Bitcoin client plus a load of databases to be able to browse the block chain. That site is not necessarily trustworthy, and is not necessarily always up. What if I want to confirm a transaction by the owner of the site? How can I trust that the block explorer is showing me the truth? What if someone hacks blockexplorer.com?

Instead, the main block chain management library will behave as a local block explorer for every user. Checking the balance of any address will be a query to that local explorer, which will know the answer.

There is an advantage to the network in doing this as well: it encourages downloading of the entire block chain. The more copies of that, the better.

Bookmarking

Given that every user will have a local, high speed block explorer, we should give them some enhanced facilities. It should be possible to bookmark and watch any Bitcoin address; even if it's private key is not local. It should also be possible to watch keys in a unidirectional manner. There are a few reasons:

  • Private key is stored offline. For a savings wallet, a user might remove their private key from the local hard disk, print out a copy and store it in a safe-deposit box (say). They should be able to watch the balance of that address without having to go to the safety deposit box and load up the key to their system.
  • Services like mybitcoin give a user a key; receipt on which get directed to their mybitcoin account. It's convenient for them to be able to watch that account without having to log in to the mybitcoin service. Outgoing coins from these addresses have nothing to do with the user though, so it should be possible to set a bookmark as only watching incoming transactions.
  • Similarly, they may be given a time limited deposit address. It should be possible for them to specify that time limit in the bookmark.

Instant transaction confirmation

Receiving coins is a nerve-wracking experience. When you send coins from, say, Mt.Gox to your local wallet, you want to know as soon as possible that they've arrived. Transactions actually happen very quickly.

  • Transaction created by owner of coins [CREATED]
  • Transaction broadcast to network [CLEARING]
  • Transaction accepted into a miner's pending block [ACCEPTED]
  • Block broadcast to network [CONFIRMED1]
  • Subsequent confirmation blocks broadcast to network [CONFIRMEDn]

The names in brackets give a name for the state. CONFIRMEDn is what we're looking for, the higher the n the better. However, CLEARING is an important state too; the user will feel a lot more relaxed if, when they send coins from their Mt.Gox account to their wallet, if a transaction appears on their screen saying CLEARING.

This next part won't work without a protocol change, who knows if I will ever get agreement for this. Double spends are a problem. Let's say two con men want to double spend. One is buying a Ferrari in Australia, the other in America. They are in communication and they both broadcast the transaction at the same time. The transactions spend the same coins.

The network simply drops any transaction it receives that conflicts with one it already has, and never passes it on to its peers. That means half of the network will receive the first transaction, half of the network will receive the second. Assuming the receiver node (i.e. the vendor) in each case is logically close to the conman, then each vendor sees their wanted transaction. They have no idea that a double spend has been attempted. Instead they will have to wait for sufficient blocks to be generated to decide on "true" chain.

Here is the change needed: when a node drops a transaction it doesn't just drop it, it broadcasts the fact of the rejection with a new inv message type. Let's call it MSG_REJECT_TX. These inv messages get passed along exactly as normal; and the nodes respond with a tx as normal. However, the nodes know that they are requesting a rejected transaction. In this way a double spend will be detected by both halves of the network. Given that it takes about 10 seconds for a transaction to propagate, a node will know about a double spend within ten seconds and can tell the vendor close to instantaneously.

Decouple GUI

The official client only vaguely separates the GUI from the protocol. For example, in main.cpp it uses constants from wxWidgets and tries to show a message box.

The GUI shouldn't be referenced at all in this part of the code.

Far better monitoring

With the block chain code separated from the wallet code, it should be possible for a website to keep its wallet data in its relational database. Further, it should be easy to extend the block and wallet handling to manipulate the target database automatically.

I'm thinking in particular of removing the need for web sites to regularly poll the Bitcoin RPC mechanism. Instead the appropriate records should just appear in the database.

A similar extension could make http calls associated with Bitcoin events.

SSL

Encryption between nodes would help hiding Bitcoin activity from ISPs and governments. It would also make traffic analysis harder.

No more IRC

IRC is a poor way of boot strapping the network. I plan to just remove it.

Time

If my node has its time set by NTP, why should I allow it to be voted to a potentially worse average by the network?

Clearing

A Bitcoin balance, just as at a bank, isn't the whole story. At your bank, when you deposit a cheque, your balance doesn't go up instantly. Instead you get two balances:

Balance:       25.32
Uncleared:    125.32

Clearing is the time between a transaction being committed to and it being settled. In the case of a cheque, the bank knows about the cheque when you deposit it, but you must wait for that cheque to pass through the inter-bank clearing system before it registers as cleared funds in your account. Cleared funds are those that you can draw on.

With banks, they have no idea when you have written a cheque, nor who you have given it to until that person deposits it and it passes through clearing. Your bank balance therefore can't show uncleared outgoing funds. The concept exists in both directions though.

Bitcoin would benefit from using the same ideas and nomenclature, but thanks to the way the technology works it can supply clearing information for both withdrawals and deposits.

Cleared balance:           25.32
Uncleared deposits:       100.00
Uncleared withdrawals:   (  5.32)
                                --------
Uncleared balance                 120.00

The uncleared balance will eventually become the cleared balance, and the uncleared deposits and withdrawals will eventually reach zero.

In the UK banking system, the banks could originally wait as long as they wished before declining a cheque. The government passed a law telling them that they couldn't do this any more, and that there must come a time when they honour a cheque even if they later find they would have declined it. This so-called, "certainty of fate" is six days in UK banking.

Bitcoin can do better than this. No transactions are ever really declined; they cannot be once they are sent. However, the receiver is worried primarily about successful double-spend attempts. Received wisdom is that six confirmations (approximately one hour) is good enough to be able to rely on the block chain not experiencing a reorganisation (and unclearing previously accepted transactions).

Transactions with less than six confirmations should therefore be considered "uncleared" and shown as such in the balance summary.

The reason this is important, is that many new users make a payment and see their balance instantly drop. Whereas they don't see it instantly increase when they receive a payment. The above four figures will give them confidence that clearing is in progress, and it makes it obvious what has happened. Many people are familiar with the idea of clearing already, and so it is using ideas they already understand to explain the operation of Bitcoin. What's more, they'll be very pleased to compare the banking system's 3-6 day clearing process with Bitcoin's one hour clearing process, and near-instant announcement of deposits.

"I PAID!" Message Signing

Let's say you want to prove to a third party that you paid a bill. It's not easy. The hard part is proving that the address you sent to was really owned by the vendor. However, we'll assume that you've got signed emails showing the receive address. Given a publicly available transaction, how do you prove that you were the sender in it, without revealing the private key for that send address?

The answer is the ability to sign an arbitrary message with your private key for that address or group of addresses.

"Dear Third Party,

I sent 25 BTC to Mr Liar in transaction 1234567...89abcdef; my proof
of this is that I have signed this letter with the keys used by the
sending addresses in that transaction.

Yours,

Injured Party"

You should be able to feed this into the Bitcoin client and have it sign it with the appropriate private keys.

Reject duplicate transactions

It has happened that an identical coinbase transaction has entered the block chain twice. This is a gross error. It is impossible to spend the outputs of both of these transactions, since transactions refer to other transaction IDs, not blocks.

It's perfectly possible to reject a transaction's entry into the orphan pool if the same hash has already been used elsewhere.

This is only really relevant for miners.

We could also do with a solution for the problem. Consider someone who pays, say, their ISP bill in bitcoins. Every month, 1 BTC from address A to address B. In the event that they fund address A with 1 BTC in advance to make this payment (i.e. there will be no change) then it would be possible to make the same transaction, and hence the same hash. The solution is to add something to the transaction generation that changes with time... let's say the time.

That will add an extra template to the allowed transaction formats list, but is pretty essential.

Long term addresses

Let's imagine I have my savings stored in a single bitcoin address. I want that address to be valid for fifty years. I keep it (mostly) offline and load it in (using the simultaneous and split wallet support mentioned above) to withdraw some savings (depositing obviously doesn't need the private key, and the bookmarking facility will let me monitor the balance). The current client will return the change to a different address. For preserving my anonymity that is mostly the right thing to do; in this case it isn't though, I withdraw 1 BTC from a 5000 BTC savings address and 4999 BTC go to a new address -- one that I haven't printed out and stored in a safety deposit box.

The solution is to store a per-address flag saying whether that key should have change returned to it or not.

Receipts

This is slightly outside the realm of responsibility for a client, but it would need support in the client to work.

Nobody is going to keep copious notes when they buy things with bitcoins. With a bank, at the end of the month I get a statement that tells me where I spent my money. With Bitcoin all I would get is a list of addresses. My solution to this is to have a secondary distributed system (or centralised, it doesn't matter), where vendors can publish the details of a particular sale. Even if it was just their name.

People will obviously not want that information published, so it needs to be encrypted if it is going to be publicised. The solution is to use the public key of the sender of coins to encrypt the details of the receipt, then store it in a distributed database against the transaction hash. The client then makes a web lookup for all expenditure on a particular address, and receives (of course) a load of encrypted messages. Being the owner of the matching private key means that they are (uniquely) able to decrypt those messages, which the client would automatically do and copy the message into its local database.

I think this can be done with ECDH using the exact same keys as are used for signing. I also can't see how it breaks security as the private key is never used, and if it were possible to break a private key simply by generating known messages to it, then it wouldn't be very secure anyway.

As a bonus, the message could be signed by the receiver of the coins so that the client has a way of verifying that it came from the merchant. This stops people from spamming transactions. If the signature signed the encrypted message, the receipt server could verify too, and discard messages from anyone else.

Deanonymising Prevention

Dan Kaminsky came up with a method of deanonymising Bitcoin. The rule is essentially, "the first IP to relay a transaction for a given identity, is the identity"; this obviously requires maintaining a massive level of connectivity, but that's not outside the realms of possibility. Some features to prevent that:

  • Never send a created transaction to inbound connections.
  • Relay a transaction to connected nodes in a random order, at random times.

About

Alternative bitcoin client

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published