It’s been great to be on the Chat with Traders podcast on 7 September 2022 for episode #243.
This write-up is meant to complement the episode and provide additional background on the warrant arbitrage trades I executed between 2015 and 2019.
Before we start, episode #243 was Aaron’s last recording, and I’d like to take a moment to thank him for all the great content he’s produced during the past years. Lots of kudos to you, Aaron! I always loved listening to your interviews with some of the world’s most interesting traders, and I’m glad that Tessa Dao will be continuing the show with the same passion and move it forward. All my best to both of you.
This is a story about me exploiting “arbitrage” opportunities in the German DAX warrants market. I put arbitrage in quotation marks as – technically speaking – the trades weren’t pure arbitrage trades (riskless winning trades). I needed to accept residual vega, gamma, and counterparty-behavior risks. However, as you will read further down below, it was very close to an arbitrage.
It all started in 2015 and lasted for about 4 years. During that time, I was able to realize strong risk-adjusted returns without large drawdowns. I rarely had a down-day, and never a down-week.
The downside: It wasn’t scalable for larger amounts of capital. Moreover, it was very time-consuming and – at times – stressful.
The following chart shows my performance between September 2015 and February 2019. The x-axis shows the total number of trades. I started with 79 paper trades, shown in blue, and then continued with 1,321 live trades before I stopped trading when I noticed a consistent decay in performance.
The trade was to simultaneously buy put and call warrants. I created long positions in straddles and strangles. The counterparties to these trades were investment banks (warrant dealers) such as Goldman Sachs, BNP Paribas, Unicredit, UBS, Deutsche Bank, and some others.
Sometimes, and especially during times of strong down-moves in the DAX index, these banks were too slow to update (remark) their DAX implied volatilities, resulting in them offering their warrants below fair value and with too low of a bid-offer spread. When I spotted this, I entered the position and waited for the bank to remark its vol surface to market. I would then close the position for a profit. Usually, the hold time was between 30 seconds and 10 minutes.
A vanilla straddle or strangle position is always long vega and gamma. You may know that I’m a big fan of positive convexity when it comes to trading (and life), so this is a position I like. Like a trend following position, this is a trade with an ex-ante known risk (warrants premium) and essentially unlimited upside. That’s the ZIP-code I like to trade in.
For these trades to work I needed the DAX to move. The more it moved, the better – especially to the downside, as large downside moves would allow me to realize vega and gamma gains.
In terms of maturities, I focused on short-dated warrants with expirations between 2 and 6 weeks. That’s where most of the liquidity was, and that’s where most of the gamma is. It’s also where most of the mispricings happened as the short end of the vol curve tends to react faster and stronger to asset price moves than the back end, i.e., there’s higher vol of vol at the short end. For example, when the S&P 500 index drops, the VIX index, which is short-dated, usually moves higher while the long-dated vol expectations may barely move, resulting in an increased backwardation of the vol term structure.
DAX Warrants and Options
The DAX warrants are issued from the dealer’s balance sheet and “wrapped” into a debt instrument (e.g., a note). Usually, this note is unsecured/uncollateralized dealer “paper,” meaning the note holder assumes the issuer’s credit risk.
In the case of regular DAX options, the counterparty risk is to the clearing house of the EUREX exchange rather than to an issuing entity. Therefore, from a credit risk perspective, warrants should trade at a cheaper price than comparable EUREX-listed options as the warrant price should discount the issuer’s default risk (essentially the CDS price up to warrant’s expiration date). However, the opposite was the case. Both the bid and offer prices of warrants were quoted above the bid prices of equivalent regular DAX options, preventing the trader from creating a synthetic credit trade: buying a deep in the money call warrant at the offer (assuming issuer credit risk) and selling the equivalent deep in the money EUREX call option at a higher bid.
The German retail structured products market isn’t limited to DAX warrants. The list goes on and includes warrants on other equity indices, single stocks, commodities, and FX, as well as more exotic products such as autocallables, bonus notes, reverse convertibles, or range accruals – to name only a few. Occasionally, I was able to create arbitrage trades in these products, too.
Dealers offering these products operate in a complex and IT-intensive business. Tens of thousands of different products with non-linear derivative payouts need to be quoted in real-time. Dividend estimates, implied vols and skews, repo rates, and many other pricing parameters need to be kept current to prevent a mispricing. This is where things can easily go wrong. And this was one of the sources of my trading edge.
An important difference between warrants and options is that warrants have a one-sided market whereas options have a two-sided market. Using a margin account, a trader can go long and short options on the EUREX. However, traders can only buy warrants from a dealer. Shorting warrants isn’t possible because dealers don’t run margin and clearing operations for their retail products, and because they don’t want to assume the credit risk of retail clients. This makes the warrants market one-sided: The trader can buy to open a long position and sell to close, but the trader cannot open a short and cover later. That 1-sidedness is a major advantage for the dealer – more on that later.
In contrast, the EUREX market is the “true” market as option prices are determined through a two-sided price discovery process. Traders can put bids and offers into the limit order book. There are also several market makers in DAX options at the same time, as opposed to the single market maker situation pertaining to a particular warrant, namely the dealer (e.g., Deutsche Bank would only quote on their own warrants but not quote on Morgan Stanley warrants).
In the 2015-2019 period, DAX warrants had a 1 point spread – i.e., much tighter than the B/O spread on EUREX. Though the dealers were aware of this, they didn’t mind it since they
- could sell their warrants at above market prices to retail traders who, on average, tend to lose money when holding long positions in calls and puts;
- would use the notes in which the warrants were wrapped as a convenient source of balance sheet funding;
- were the exclusive market maker, allowing them to quote away from fair market prices;
- would only sell warrants and not allow their clients to go short.
Since, on average, I’d hold my arbitrage positions for less than 5 minutes, I could take advantage of their too-small B/O spread. It allowed me to move in and out without a lot of friction.
Here’s what I did. I ran an Excel spreadsheet with an API connection to Interactive Brokers. I had a real-time EUREX price subscription through at Interactive Brokers and streamed the DAX option bid prices into the spreadsheet.
That spreadsheet was also connected to several discount broker APIs through which I pulled the warrant offer prices from dealers such as Goldman Sachs, Deutsche Bank, DZ Bank, UBS, and so on.
This allowed me to compare all the warrant offer prices to the equivalent EUREX option bid prices in real-time. As mentioned above, the warrants traded at higher prices than the comparable options.
Using a bit of code, I took a snapshot of the price differences every 5 seconds and saved the information to a database.
I could now run simple analyses on these price differences throughout the day. For instance, I would calculate percentiles to determine whether a particular dealer was getting cheaper or more expensive relative to DAX options throughout the day. Since I could only buy warrants, I was interested in “cheap” for the entry and “expensive” for the exit.
All of this required a lot of preparation and manual work as I needed to manually input thousands of warrant ISINs into the spreadsheet. The ISINs were needed to pull the data from the retail broker API, and as you might imagine, all of these APIs were working slightly differently.
Next step: An alarm would go off once my percentile calculations showed that a particular dealer had become too cheap relative to that day’s price history.
I would then have a look at the market to see what’s going on. Ideally, I would see the DAX price falling and the VDAX index rising. The VDAX index is the VIX index for the DAX.
Next, I would run a macro to create several delta-neutral combinations of call and put warrants from one or more dealers. Most of my trades were in 15 to 25 delta calls and -15 to -25 delta puts (strangles).
I preferred strangles over straddles because strangles are “slower.” Their lower delta gave me a bit more time for execution, which reduced my slippage risk. That was important because the DAX index usually showed large price moves at the time I entered the trade. I needed some stability because I couldn’t trade the strangle as a package. Both legs had to be entered individually, one after the other, both when entering and exiting the position.
Entering these trades was something I practiced with my paper trades at the very beginning. It had to be a fast and error-free routine. Every mouse click had to be fast. I copied the call and put warrant ISINs into two separate order masks, requested quotes, checked the quotes and spreads against current EUREX prices, had another look at the DAX and VDAX as I wanted to see that both a still moving in the right direction, and then executed – all within 5-8 seconds for both legs.
I had accounts with many different retail brokers. Sometimes a certain broker would offer a zero-cost trading month and I would then take advantage of that offer by executing through them rather than through a broker that would charge me commission. The regular commission was 3-6 EUR on average per side, i.e., for a round-turn (2 x 2 trades) it would sum up to EUR 16 assuming EUR 4 per side.
Behind the scenes, the retail brokers RFQ’d against the issuing dealer when I clicked the “request price” button inside their order mask. The dealer would return a quote and keep it live for about 5 seconds. It’s like a countdown clock. Miss it and you need to RFQ again.
The brokers I used had different latencies to the dealers. That’s something I needed to consider when RFQ’ing as the quotes from DZ Bank, say, tended to come in 1-2 seconds slower than the quotes from UBS.
Sometimes the arbitrage was so attractive that the execution venue didn’t matter much. I would happily execute through the most expensive broker as all I needed to do was to get into the trade as fast as possible. Occasionally, I sent my orders to a warrants exchange (e.g., the Stuttgart or Frankfurt exchanges) where I paid even higher fees because the local specialist would charge a fee on top of the execution commission. I did this because exchange executions are subject to the exchange rulebook and local regulations, which offer traders a higher level of protection compared to an OTC broker execution. When I spotted severe mispricings and very lucrative arbitrages I thought it wise to use the extra cover provided by exchanged regulations.
The main reason DAX warrants became too cheap is because dealers were too slow with the recalibration of their in-house vol surface. DAX prices would drop and implied vols would spike, but the dealer’s auto-update function could not keep pace and/or nor recalibrate properly to the new skew. That’s essentially what my code spotted and what my spreadsheet displayed. I then opened the strangle position, waited for the dealer to recalibrate higher, and then exited the position with a nice vega PL.
Markets are orderly most of the time and the dealer’s auto-update function works well in these situations. When there are large market moves, dealers are usually quick with their recalibration, too. However, it requires the trader to do it manually. The trader wants to be fast as any delay could cause the warrant’s offer price to trade below the equivalent EUREX bid price, which would allow traders buy the cheap warrant and sell the expensive option for a net credit (assuming counterparty risk).
Because dealers have tens of thousands of products, keeping everything up to date in real-time is difficult.
To remain undetected and cover my tracks, I aimed to trade the call and put with different dealers, e.g., buying the call warrant from Unicredit while buying the put warrant from BNP Paribas. I usually traded 10-15K warrants per side. Splitting the trade meant that the dealer would only see one side, reducing the chance of them becoming suspicious.
For when they became suspicious, or had realized what had happened to them, the “dance” began.
The dance goes as follows (no strict sequence, just examples):
- Move 1, the dealer takes the warrant I bought off the auto-quote machine. Not all warrants, just the warrant I’m long. Remember that to close the position I need to RFQ a bid through the broker. This RFQ may now no longer be answered, keeping my trapped.
- Move 2, the dealer widens the B/O spread of that particular warrant from 1 point to 2 or 3 or 5 points. They would still quote, but paying this large spread would destroy my PL on the exit.
- Move 3, the dealer would mark-down the implied vol of the warrant I traded while moving the vols for all other warrants higher, and it would no longer show offers for the warrant I’m long. It would only show the now far-too-low bid.
- Move 4, the dealer would stop quoting everything and claim to have IT issues or a fire drill.
Dancing along, I would call their hotline, presenting myself as “Helmut Meyer” (70 years of age, retired, and speculating in warrants for fun). I would point out that I had spotted an interesting inconsistency in a certain warrant price and that I wasn’t sure what it meant. I said that I’d really like to trade but that I’m confused by these prices.
They knew it was me who called and I only got “eff off” answers (e.g., we’ve got latency and IT issues). So, I hang up and then called them again 5 minutes later in the name of Mr. Dieter Schmidt with a change in voice and tone. I said that I had a position which I wanted to close, that I had evidence of unfair pricing, and that my lawyers would contact them if they didn’t give me a fair price. Sometimes this worked, but most of the time it didn’t.
Note that while the dance is going on, the dealer is essentially long an option – an option on time. They could sit it out.
- If the DAX turned around to the upside and vols came down, they could restart their quote machine and show me the now fair and lower bid and I would need to take the loss.
- If the DAX dropped further and vols increased even more, they could widen their B/O spread even more and continue to mark down their vols, which could force me to keep the position overnight and pay theta. These overnight trades were the most stressful trades as they had nothing to do with the original trade premise. It was now me against them. Dealers don’t want to stay mismarked for days and weeks as that could damage their reputation and be spotted by the media, so their option on time was limited to a few days. During that time I would need to hedge elsewhere, e.g., by selling on EUREX. However, it sometimes also created interesting new arbitrage trades as I could sniff out other products which were affected by their mismarked vols – products which were too cheap and which still had offers. I usually spotted these opportunities in the pre-market session between 8 and 9 am when the EUREX market is not yet lit and dealer vols are priced very conservatively as they are derived from the overnight price action in S&P 500 and Nikkei.
In 85-90% of all cases I was able to trade in and out without doing the dance. I was willing to incur higher commission costs by trading smaller clip sizes as this would leave a smaller footprint (e.g., 4 x 2,500 warrants instead of 1 x 10K warrants). And I made every effort to spread my trades across different dealers and many different strike combinations to stay undetected, even when the dealers didn’t have the best prices.
The next chart shows how I normalized my PL. In my trend following trading system I normalize PL in terms of ATRs, and for my warrant trades I normalized them in terms of B/O spreads. When the B/O spread on a warrant is 1 cent, the total spread cost per side for 10K warrants is 10K x 0.01 EUR = 100 EUR. Thus, for a strangle consisting of 10K calls and 10K puts the cost is 200 EUR. Let’s assume that I could close the trade with an 800 EUR gain. In this case I had made 4 spreads (800 EUR / 200 EUR). My live trades realized an average spread PL of 1.26 spreads.
And here are some trade statistics:
I had many scratch trades, exiting for a PL of about zero, but like a trend following trader I also had some nice outlier trades. These outlier trades were driven by large increases in implied vols and substantial gamma PL, sometimes moving the put delta from -15 to -60 in a short period of time.
Alas, I also had a few outliers to the downside. That happened when I was trapped in the dance and couldn’t get out of the position.
My arbitrage method generated a very consistent PL; however, I couldn’t really scale it for size. I needed to watch the screen all the time as I had to be quick when the alarm went off. Eating lunch at the wrong time of the day or walking the dog could result in missing the only attractive trading opportunity of the day.
Since I wanted to do other things during the day, I was motivated to automate the strategy – and I did, to an extent at least. I couldn’t automate everything though. The obvious trades, i.e., the lowest-hanging fruits, could be automated (and those had a smaller PL expectancy). However, automating these trades was risky because it could result in single leg executions, i.e., produce a single call or put position, which creates a net delta position. That’s not what I wanted. Single leg executions can also happen when executing manually, but when I saw this and knew that the dance was about to start, I was quick to take the 1-point B/O loss and close the single leg. My automated system couldn’t detect if a dance was going on though, which is why these trades played a very minor role in the overall PL.
To end this story on a funny note, the trading volume I generated made me a “platinum” client of all these retail brokers. I know this because they invited me to social events every couple of months, e.g., to the lounge of the FC Bayern Munich soccer club (with dinner and champagne included of course). To make it interesting for us traders, the brokers also invited a dealer to the event. The dealer would usually give a presentation about structured products and warrants. So here I was, Helmut Meyer, talking to the dealer on the other side of my trades about warrant trades while sipping champagne on their dime. Little did they know.