Le 1er août 2012, Knight Capital Group, une entreprise de trading haute fréquence, a connu un désastre financier sans précédent aux premières heures de l’ouverture de la bourse. Quelque chose a très mal tourné dans le code qui avait été introduit pendant la nuit. Il s’agissait d’un algorithme de négociation à haute fréquence conçu pour acheter et vendre des quantités massives d’actions dans un court laps de temps. La combinaison d’un mauvais timing et de mauvais ordres a conduit à des résultats désastreux.
Knight Capital Group est une société américaine de services financiers d’envergure mondiale qui exerce des activités de tenue de marché, d’exécution électronique, de vente et de négociation institutionnelles. En 2012, Knight était le plus grand négociateur d’actions américaines, avec une part de marché d’environ 17 % sur le New York Stock Exchange (NYSE) ainsi que sur le Nasdaq Stock Market.
Il a fallu 17 ans de travail acharné pour faire de Knight Capital Group l’une des principales maisons de courtage de Wall Street. Et tout a failli s’arrêter en moins d’une heure. Ce qui est arrivé à Knight le matin du 1er août 2012 est le cauchemar de tout chef d’entreprise : une simple erreur humaine, facilement repérable a posteriori mais presque impossible à prévoir, a menacé de mettre fin à l’entreprise.
Chez Knight, un nouveau logiciel de négociation contenait une faille qui n’est devenue apparente qu’après l’activation du logiciel à l’ouverture de la Bourse de New York (NYSE) ce jour-là. Le logiciel erroné a entraîné Knight dans une frénésie d’achat, s’emparant de 150 actions différentes pour un coût total de plusieurs milliards de dollars, le tout au cours de la première heure d’ouverture de la bourse.
Selon les règles de la bourse, Knight aurait dû payer ces actions trois jours plus tard. Cependant, il n’y avait aucun moyen de payer, étant donné que les transactions n’étaient pas intentionnelles et qu’elles n’avaient aucune source de financement. Les seules alternatives étaient d’essayer de faire annuler les transactions ou de vendre les actions nouvellement acquises le même jour.
Knight a tenté de faire annuler les transactions. La présidente de la Securities and Exchange Commission (SEC), Mary Schapiro, a refusé de le faire pour la plupart des actions en question, et cette décision semble avoir été la bonne. Des règles ont été établies après le “flash crash” de mai 2010 pour déterminer quand les transactions doivent être annulées. La frénésie d’achat de Knight n’a pas fait grimper le prix des actions achetées de plus de 30 %, le seuil d’annulation, sauf pour six actions. Ces transactions ont été annulées. Dans les autres cas, les transactions ont été maintenues.
Des délais serrés pour les développeurs
Les développeurs ont été chargés de porter leur robot HFT (High-frequency, en français, transactions à haute fréquence) sur un service API NYSE à venir, dont la mise en service a été annoncée moins de 33 jours plus tard. Ils ont donc entamé un sprint de 80 heures par semaine. Le robot HFT était écrit en C++. Pour ne pas avoir à recompiler une seule fois, l’architecte en chef a décidé de conserver exactement la même classe et la même signature de méthode pour leur méthode PowerPeg::trade(), qui était leur robot de test automatisé qu’ils utilisaient depuis 2003. Cela signifiait également qu’ils n’avaient pas à mettre à jour le WSDL (Web Services Description Language, un langage de description fondé sur XML) pour les clients qui utilisaient le robot.
Ils ont supprimé l’ancien code mort et mis en place le nouveau code. Un code qui faisait appel à une logique réelle, au lieu du code de test, qui était conçu, par défaut, pour acheter l’offre la plus élevée qui lui était faite.
Ils l’ont testé, ils ont écrit des tests unitaires, tout semblait bon. Ils ont donc décidé de le déployer à 8 heures EST, 90 minutes avant l’ouverture du marché. Les testeurs d’assurance qualité l’ont testé en production et ont donné le feu vert. Tout le monde était très heureux. Ils avaient réussi. Ils avaient respecté le délai serré et déployé l’application avec seulement 90 minutes d’avance…
Ils se sont immédiatement rendus à une réunion de sprint standup puis à une réunion de sprint retro. Conformément à la politique de leur bureau, ils ont laissé leurs téléphones (en sourdine) à leur bureau.
« Tuez les serveurs !!! »
Pendant la rétro, les marchés ont ouvert à 9:30 EDT, et le nouveau bot a simplement commencé à acheter l’offre la plus élevée pour tous les titres de sa liste d’achat. Les marchés n’ont pas réagi de manière très anormale, parce qu’ils avaient simplement l’air d’être haussiers. Mais le bot achetait environ 5 millions d’actions par seconde… En l’espace de 2 minutes, les alarmes se sont déclenchées dans leur secteur bancaire interne… un pourcentage énorme de leurs 2,5 milliards de dollars de liquidités d’exploitation était en train de s’épuiser, et rapidement !
De nombreuses personnes ont essayé de contacter les développeurs, mais ils se trouvaient dans un bureau éloigné à Hoboken en raison du prix élevé de l’immobilier à Manhattan. Leurs téléphones étaient éteints et personne ne se trouvait devant leur ordinateur.
Le PDG a été vu en train de faire courir des gens dans les couloirs du bâtiment, en criant, et finalement les développeurs l’ont remarqué. 11 minutes s’étaient écoulées et les robots avaient acheté pour plus de 3 milliards de dollars d’actions. Les réserves de liquidités étaient épuisées. La société avait de sérieux problèmes…
Aucun des développeurs n’a pu trouver la source du bogue. Le PDG, désespéré, a demandé des solutions. L’un des développeurs a crié : « TUEZ LES SERVEURS !!! ».
Des techniciens du centre de données situé à côté du bâtiment de la Bourse de New York ont trouvé les 8 serveurs sur lesquels fonctionnaient les robots et les ont détruits à l’aide d’un câble d’incendie. Et finalement, au bout de 37 minutes, les bots ont cessé d’opérer. Perte totale sur papier : 10,8 milliards de dollars.
La SEC et le NYSE ont refusé de rétablir les transactions pour toutes les actions sauf 6, les pertes sur papier étaient encore de 8 milliards de dollars. Impossible de payer. Goldman Sachs est intervenu et a proposé d’acheter toutes les actions à un prix lucratif de 457 millions de dollars, ce qu’ils ont accepté. Au final, la société a perdu près de 500 millions de dollars et tous ses clients ont quitté la société, qui a fait faillite quelques semaines plus tard.
Quelle était la cause de ce bogue ? Une grossière erreur humaine lors de la mise en production
L’administrateur système avait refusé d’implémenter un pipeline CI/CD, qui en était encore à ses balbutiements, probablement parce que c’était son travail à plein temps. Il y avait 8 serveurs qui hébergeaient le bot et quelques clients sur les mêmes serveurs.
Il avait tapé et collé les bonnes commandes rsync pour obtenir le nouveau binaire C++ sur les serveurs, à l’exception du serveur 5. Dans son cas, il y avait un 5 supplémentaire dans le nom du serveur. Le rsync a échoué, mais comme il a collé toutes les commandes en même temps, il ne l’a pas remarqué…
Comme le code utilisait exactement la même signature de méthode pour la méthode trade(), le serveur 5 était heureux d’acheter l’offre la plus chère qu’on lui proposait, parce qu’il exécutait le logiciel de trading de test Sad Path. S’il avait changé la signature de la méthode, il n’aurait pas fonctionné et le bogue ne se serait pas produit.
À 9:43 EDT, les développeurs ont décidé collectivement de faire un “rollback” à la version précédente. C’était la pire erreur possible, car ils ont ajouté le code Power Peg mort aux 7 autres serveurs, ce qui a provoqué une croissance exponentielle des problèmes. Il a fallu environ trois minutes pour que quelqu’un de la direction financière en soit informé. À ce moment-là, plus de 50 millions de dollars par seconde étaient perdus à cause du bogue.
Ce n’est qu’à 9:58 EDT, lorsque tous les serveurs ont été détruits, que les transactions se sont arrêtées.
Leçons tirées du fiasco de Knight Capital en matière de tests de logiciels
Rick Lane, qui était alors directeur technique de Trading Technologies à Chicago, a souligné que ces algorithmes de trading sont développés très rapidement, car ils sont conçus pour saisir des opportunités fugaces, et qu’une bonne gestion du changement peut être reléguée au second plan par rapport à la rapidité.
Il a proposé à l’époque quatre façons d’améliorer les tests de logiciels et de réduire les risques :
- Améliorer la gestion des changements et de la configuration : Le fait de conserver le code de test et le code de production dans des “bacs à sable” différents est une pratique très répandue pour réduire les risques. Chez Zappos, l’équipe dispose d’un processus distinct et plus rigoureux pour le code qui touche aux données sensibles des clients et aux informations financières. Etsy, quant à elle, déploie tout le code en production, mais atténue ce risque grâce à la technique n°2.
- Améliorer le contrôle de la production : Lane suggère d’utiliser des processus automatisés pour détecter les erreurs et envoyer des alertes. Jeffery Reeves, rédacteur en chef de InvestorPlaceMedia, recommande que des personnes surveillent les volumes de transactions et fassent preuve de discernement. Les entreprises qui effectuent un grand nombre de transactions automatisées ont tout intérêt à avoir les deux.
- Considérer les tests comme un processus de gestion des risques de haut niveau : « Dans de nombreux cas, les sociétés commerciales estiment qu’elles n’ont pas assez de temps pour effectuer des tests traditionnels en raison de la brièveté de ces opportunités éphémères », a expliqué Lane. Paradoxalement, de nombreux bogues ne seraient pas détectés par les tests traditionnels, car il s’agit de risques de configuration. Le logiciel peut avoir fonctionné correctement, mais au mauvais endroit, au mauvais moment ou à partir d’un code de test qui était en production. Le type de testeurs qui « cliquent sur ceci, cliquent sur cela, s’assurent que ces chiffres correspondent », comme les décrit Lane, ne pourrait pas trouver de tels bogues. Une meilleure gestion des risques est nécessaire.
- Renforcer les contrôles internes sur les transactions à fort volume : Il est possible que la défaillance de Knight Capital ait pu être évitée grâce à un simple bouton sur lequel un humain devait cliquer, en particulier lorsque le volume atteignait un certain niveau. Un tel contrôle ne se situerait pas au niveau du programme, mais plutôt au niveau de l’API publique. Tant que de tels contrôles externes n’existent pas, nous ferions bien de les intégrer dans nos programmes de passerelle.
source:developpez