top of page
  • Writer's pictureChris

Banking #1: Core Systems Modernization

Table of Contents


Why Modernize the Core?

The need for banks to modernize their core systems is driven by a combination of customer expectations, market dynamics, and regulatory requirements. Embracing digital transformation in core banking systems is no longer a choice but a necessity to remain competitive, compliant, and relevant in the rapidly evolving financial landscape. Modernized core systems enable banks to offer personalized, efficient, and transparent services, meeting the demands of today’s customers and regulators while staying ahead in the competitive market.


Customer Demand

Modern banking customers, especially millennials and Gen Z, have grown up in a digital-first environment. Their expectations from banking services are fundamentally different from previous generations. They seek convenience, speed, and digital fluency in their banking interactions.


Today's customers expect a more personalized banking experience. They want services that recognize their unique needs and preferences, offering tailored financial advice, customized product recommendations, and holistic treatment of their financial portfolio.

Banks need to shift from transaction-based interactions to a more relationship-oriented approach. Modernizing core systems is essential to integrate various customer touchpoints and provide a comprehensive view of each customer’s banking relationship.


Market Demand

The rise of FinTech companies, which operate with lower costs and more agile business models, is a significant driver for core system modernization in traditional banks. FinTechs, leveraging modern technologies, are able to offer competitive, innovative services more efficiently.


In response to FinTech competition, banks are rethinking their economic models. Modernizing core systems can lead to more efficient operations, reduced costs, and the ability to innovate more rapidly, thus enabling banks to offer services at competitive prices while maintaining profitability.


Modern core systems are more agile, scalable, and capable of integrating with emerging technologies like blockchain and artificial intelligence, positioning banks to better compete in a rapidly evolving digital financial landscape.


Regulatory Demand

Banks face an ever-evolving landscape of regulatory and compliance requirements. Modern core systems are essential to manage and respond to these changes effectively. This includes adapting to regulations around financial transparency, risk management, and customer data protection.


Regulators are increasingly mandating that customers have more control over their data. Modernized core systems are better equipped to handle such requirements, enabling banks to offer customers the ability to manage their data and consent preferences more easily.

Modern core systems facilitate improved reporting capabilities and greater transparency in areas like loan portfolio management. This is crucial not only for regulatory compliance but also for building trust with customers and stakeholders.


Core Systems in Banking

Core systems in banking refer to the essential software and hardware infrastructure that support the bank's primary functions and operations. These systems are the backbone of a bank, facilitating a wide range of activities. Examples of these systems include Customer Information Systems (CRM), Deposit and Loan Systems, Payment Processing, General Ledger, Compliance and Reporting, and Risk Management. The efficiency, reliability, and capability of these core systems directly impact a bank's ability to serve its customers and operate effectively in the market.


The capabilities of a core banking system can be segmented into the following 3 layers.


Foundation Layer – Core

At the foundational level, the core banking platform includes crucial components such as accounting systems, general ledgers, and transaction processing logic. This layer is responsible for the essential functions of posting to the general ledger. In some architectural models, databases and data control mechanisms are also situated at this foundational level. It acts as the structural backbone supporting all banking operations.


Configuration Layer - Intermediate

The intermediate tier comprises the configuration layer. This segment contains a more abstracted codebase designed to define and manage banking operations. It facilitates the setup for launching new products or services and handles account servicing. The layer includes shared resources that are utilized across various products, services, or channels. Elements such as the Master Customer Information File (Master CIF), authentication services, and critical functions like credit risk management and compliance services are housed here. The focus is on delivering both versatility and specificity, ensuring that shared resources efficiently serve a wide range of banking functions.


Product / Services Layer - Upper

The topmost layer is dynamic and modular, focusing primarily on products and services. This is the business logic layer, where components can be quickly created and assembled by leveraging features from the layer below. Modernization efforts often target this layer because of its direct impact on business logic. Innovations in this tier allow for agile adaptations and efficient implementation of future changes without necessitating alterations in the foundational or intermediate layers.


3 + 1 Options

The three primary options to modernize core banking systems is augment, migrant, or replace. An additional option is to launch a new bank.


Augment the Core

For many banks committed to their legacy infrastructure, directly modernizing the core banking system can be challenging. However, augmenting the core is a viable strategy to introduce modern functionality without entirely replacing existing systems. This approach involves overlaying the legacy core with modern cloud interfaces and API overlays, enabling banks to offer contemporary services while maintaining their foundational systems. Approaches for augmenting the core include:

  • Abstracting the Legacy Core: Banks can achieve modern functionality by abstracting or segmenting the legacy core platform. This method involves building modern cloud interfaces on top of the existing infrastructure. By doing so, banks can retain their legacy core systems while simultaneously integrating new, cloud-based capabilities.Building API Overlays: The augmentation approach commonly includes constructing API overlays to abstract the legacy core. These APIs enable the creation of modern user experiences for both customers and employees and facilitate third-party integration with the bank’s infrastructure.

  • Simultaneous Development of Customer Experiences: New customer experiences can be developed in parallel with the core integration if the APIs are clearly defined upfront. This concurrent development allows for quicker implementation of modern services.

  • Phased Transition to Modern Core: This approach allows for a gradual transition to a modern core, with the legacy and modern cloud-native cores co-existing and data replicated in real-time or batches.

  • Legacy x86 and Mainframe Systems: Both x86 based systems and mainframes can be augmented. For mainframes, it often involves partnering with specialized firms like Finconecta or OpenLegacy for API building, and BMC AMI Cloud or Precisely for data offloading to the cloud.

Benefits

  • Rapid Integration: Integration with core banking systems to power modern API interfaces can be achieved relatively quickly, often within a few months, especially with support from experienced contractors.

  • Personalized Customer Engagement: By offloading data to the cloud and performing analytics, banks can gain insights from legacy systems to provide personalized offers to their customers.

  • Open Banking Implementation: This approach is instrumental in implementing open banking, allowing modern systems to communicate effectively with legacy platforms.

Challenges

  • Increased Manual Back-Office Workloads: Automating back-office processes associated with new APIs can be challenging. Some APIs may initiate manual tasks, creating new workflows or adding to existing ones.

  • Brittleness with Core Updates: As the core system is updated or adjusted, the overlaying interfaces may become brittle and require frequent adjustmentsVolume Increase in Manual Activities: Easier customer access to certain services, like transaction disputes through modern APIs, can lead to increased volumes in manual activities.


Augmenting the core is a strategic approach for banks seeking to modernize without overhauling their existing legacy systems. It offers a balance between maintaining stable, traditional infrastructure and embracing the advantages of modern, cloud-based technologies. This method is particularly beneficial for banks planning a phased transition to a fully modernized core banking system.


Migrate the Core

Migrating core banking systems is often the initial step for banks interested in modernization, focusing on reducing their physical data center footprint and setting the stage for future enhancements. This process typically involves shifting the legacy core banking platform to a cloud environment, followed by gradual refactoring and modernization. This strategy allows banks to capitalize on cloud benefits while preparing for more comprehensive system enhancements. Approaches for migrating the core include:


  • Lift and Shift Approach: The initial phase often involves a 'lift and shift' strategy, where the existing x86-based legacy core is migrated as-is to the cloud. This approach allows banks to experience the immediate benefits of cloud infrastructure without extensive initial changes to their systems.

  • Refactoring Post-Migration: Following the migration, banks typically undertake a process of refactoring the core system. This might involve breaking down a monolithic architecture into macro services or even transitioning to a microservices, event-driven platform.

  • Mainframe Migration Options: For mainframe-based systems, migration strategies can vary. One option is replatforming, using tools like Microfocus to emulate the core on the cloud. Another approach is to refactor the mainframe applications into modern programming languages using solutions like BlueAge.

Benefits

  • Rapid Return on Investment: By transitioning from capital expenditures associated with physical data centers to operating expenses in the cloud, banks can achieve a rapid ROI. This shift aligns costs more directly with business needs and usage.

  • Autoscaling and Flexibility: Migrating to the cloud allows banks to benefit from autoscaling, which adjusts resources to meet customer demand in real-time. This flexibility is a significant advantage over traditional methods that require forecasting and preparation for peak demands.

  • New Application Deployment: The cloud environment enables banks to deploy new applications and digital services rapidly, further accelerating the transformation process.

  • Innovative Workload Management: Post-migration, banks can develop, test, build, and run critical workloads directly in the cloud, accelerating transformation and innovation.

Challenges

  • Inefficiencies in Non-Optimized Architectures: Initially, ‘lift and shift’ models may lead to inefficiencies, as systems not architected for the cloud might not leverage the full potential of cloud capabilities.

  • Need for Modern Interface Development: While moving to the cloud is financially beneficial, creating modern interfaces to improve customer experiences remains a crucial part of the modernization journey. This requires additional effort to overlay the migrated system with modern front-end experiences.


Migrating the core to the cloud is a strategic move for banks aiming to modernize their operations. While it provides immediate financial and operational benefits, the journey doesn’t end there. The subsequent refactoring and development of modern interfaces are crucial for fully leveraging the cloud’s potential and transforming the banking experience.


Replace the Core

Replacing the core banking system with a cloud-native solution represents a significant shift in a bank's technological infrastructure. This aggressive approach is chosen by banks that are prepared to invest substantial resources and time into a complete overhaul of their core systems, aiming for a state-of-the-art, cloud-native platform. Approaches for replacing the core include:

  • Adopting a New Platform: Banks opting to replace their core systems choose to launch entirely new cloud-native platforms. This often involves creating a new, more efficient, and flexible technology architecture from the ground up, which is better suited to the dynamic nature of modern banking.

  • Migrating Data: The process includes migrating customer data from the legacy core to the new cloud-native system. This transition is a crucial step and requires careful planning and execution to ensure data integrity and continuity of banking services.

  • Supporting Rapid Innovation: A cloud-native core enables banks to rapidly adopt new products and services. This agility is a key factor in remaining competitive in the fast-paced financial sector.

Benefits

  • Best-in-Class Solutions: By moving to a cloud-native architecture, banks position themselves at the forefront of banking technology, benefiting from the latest advancements in process automation, agility, and performance.

  • Increased Agility and Innovation: The microservices architecture, a staple in cloud-native systems, encourages nimble technology teams and faster innovation cycles. This agility significantly enhances the customer experience and enables quicker responses to market demands.

Challenges

  • Time, Cost, and Complexity: Replacing the core with a cloud-native system is a time-intensive, costly, and complex process. The challenge lies in migrating legacy data to the new system, which often involves reformatting and integrating data from multiple legacy systems.

  • Regulatory Review and Approval: Cloud-native core systems, being relatively new, require thorough regulatory review and approval. This process varies depending on the local regulatory environment and can add to the complexity and duration of the core replacement project.

  • Building Challenger Brands or New Business Lines: To mitigate the challenges of migrating existing business to a modern core, many banks opt to establish challenger brands or entirely new business lines on their modern core platforms. This approach allows them to leverage the benefits of the modern system without the immediate need to undertake the cumbersome process of moving existing legacy operations.

Replacing the core with a cloud-native system is a bold move that signals a bank's commitment to innovation and modernization. While it comes with significant challenges in terms of time, cost, and complexity, the long-term benefits of landing on a best-in-class, agile, and customer-focused solution are immense. This approach not only enhances internal process efficiency and agility but also propels banks towards greater competitiveness in the digital banking landscape.


Launch a New Bank

An alternative strategy to modernizing core systems is the launch of a new digital bank, also know as a Challenger Bank or neobank. This approach, combining business strategy with technology decisions, is often adopted by banks seeking to establish a digital presence that their current core platforms cannot support. Approaches to launching a new digital bank:

  • Launching a Challenger Bank: Challenger banks, such as independent start-up banks with a banking license, represent a direct approach. These entities are typically FinTech-driven and focus on disrupting traditional banking with innovative products and superior customer service.

  • Starting a Digital Native Bank: This approach involves an existing incumbent bank creating a subsidiary or extension as a digital-native bank. Often termed as ‘speedboats,’ these offshoots aim to attract different customer segments and innovate more quickly than their parent banks.

Strategies for Building a New Digital Bank

  • Build Approach: Utilizing cloud-native services to construct core banking systems from scratch is a strategy often adopted by FinTechs, as well as established financial services institutions seeking bespoke solutions. This approach allows for building a long-term competitive advantage by tailoring services to specific needs.

  • Buy & Build Approach: Collaborating with specialist banking Software as a Service (SaaS) providers like Mambu, Temenos, or ThoughtMachine on cloud infrastructure facilitates speed-to-market with manageable, composable solutions. This hybrid approach is suitable for some banks, combining purchased core components with custom-built features.

  • Buy Approach: Partnering with Banking-as-a-Service (BaaS) providers, such as Starling Bank or solarisBank, offers a comprehensive solution where the provider supplies both the technology infrastructure and, if needed, a banking license. This approach allows banks to focus primarily on branding and customer experience.


Customer Segments

  • Independent Businesses: These entities are often backed by private equity or venture capital and aim to create disruptive ‘NewCo’ businesses in the market. Leveraging cloud infrastructure, they can build rapidly and cost-effectively without managing the underlying tech infrastructure.

  • Existing Banking Businesses: Traditional banks looking to attract different customer segments or innovate more rapidly may opt to establish standalone digital banks on digital infrastructure. Their goal is to operate more agilely and responsively than their larger, more established counterparts.


Launching a new digital bank offers a path for both new entrants and established banks to enter the digital banking space rapidly and effectively. Whether through building from scratch, leveraging SaaS solutions, or partnering with BaaS providers, these banks can harness the power of cloud computing to create innovative banking solutions tailored to their unique market and customer needs. This approach enables them to sidestep the limitations of legacy systems and directly address the demands of a digitally-savvy customer base.


Business Considerations

When considering the modernization of core banking systems, banks should evaluate the following business considerations:

  • Core Platform Features and Capabilities: Determine the specific features and capabilities desired in the core platform. This could range from specialized functions like Islamic banking to comprehensive transactional banking platforms, depending on the bank's target market and business model.

  • Support for Unique Business Models: Assess whether the core platform can support unique operational models, such as specific onboarding processes, underwriting standards, maintenance routines, or service models. While many core banking systems claim to be API-driven, verify if they indeed offer APIs for all desired functionalities.

  • Regulatory Compliance Across Different Jurisdictions: Ensure the chosen or developed product adheres to the regulatory requirements of each country where the bank operates. This includes compliance with data residency laws, open banking standards, and other local regulatory mandates.

  • Resource Allocation for Management and Support: Evaluate the availability and capability of the team to manage and support the new core system. Consider the resources required, including the number of operational staff or engineers needed. If opting to build a bespoke core platform, confirm if there is a competent team in place for its development and ongoing maintenance.

  • Speed of Implementing Changes: Consider the desired speed of implementing changes within the business. Some platforms may offer flexibility for easy updates, while others, especially those fully managed by external partners, may involve more complex processes and longer timelines for integrating new functionalities.

Technical Considerations

Just as the business considerations above, here are some technical considerations to keep in mind when choosing the core:

  • SaaS vs. self-hosted: Certain core banking providers offer only Software as a Service (SaaS) deployment models, where they manage the platform on behalf of the customer. In this setup, the customer securely accesses the platform. Conversely, other providers allow for more flexibility, offering the option to deploy the banking platform within the customer's own cloud environment.

  • Cloud-native platform: Banks should consider choosing a Cloud-native platform. Cloud-native platforms are typically constructed using microservices, which can scale individually in line with business growth. Additionally, some cloud-native solutions incorporate event-driven architecture, allowing for the independent scaling, addition, or removal of individual microservices. In contrast, legacy monolithic platforms lack this scalability and flexibility, often requiring updates or scaling that can impact other areas of the platform.

  • Flexibility: Customers with advanced technological capabilities, particularly FinTech companies or those requiring specific functionalities not provided by existing core providers, might consider developing their own core banking platforms, thereby gaining full control over the system. Alternatively, other customers might select partner solutions, which offer varying degrees of control. While some partner solutions offer more control over the core system, enabling the creation of entirely new products, others might only permit configurational changes.

Case Studies

Case Study 1: HSBC Augments Their Core for Better Customer Experience

Overview

HSBC is a British multinational investment bank and financial services holding company. HSBC faced challenges in delivering real-time transaction updates to customers due to limitations in their legacy core banking system.


Strategy / Solution

HSBC implemented a solution that involved migrating mainframe data to the cloud. They utilized Apache Kafka and Apache Nifi for real-time data transfer and used cloud services for managing data streams and on-the-fly data analysis. This innovative approach enabled HSBC to offer customers instant notifications such as balance updates, overdraft warnings, and personalized service options.


Cloud Services Used

The cloud service provider HSBC used was AWS (Amazon Web Services). AWS services used include:

  • Apache Kafka: Implemented in the data center, Apache Kafka was used to move data from the mainframe to the on-prem Kafka clusters in real-time. From there, the data was then transferred to the cloud using Apache Nifi. Kafka was chosen for its ability to handle large volumes of data and its ability to provide real-time data streaming.

  • Amazon Kinesis: Kinesis was used for storing and processing data in a distributed and scalable way.

  • AWS Lambda: Lambda was used as the consumer of data from Kinesis Data Streams. Each Lambda function was configured to read from a specific shard in the Kinesis stream, and the number of shards determined the number of concurrent Lambda executions. The Lambda functions processed the data records and performed various tasks such as data transformation, data cleansing, and event-driven processing.

  • Amazon DynamoDB: DynamoDB was used as part of the data service component. It was combined with Aurora to provide data as a service to the rest of the digital platform. Once in the cloud, the data was transformed and cleansed in the mapper service before being sent to the data service, which utilized DynamoDB and Aurora to store and provide the data to the rest of the platform.

Outcomes

Augmenting the HSBC core provided a better digital experience for HSBC customers by informing them in real-time rather than having them constantly check their accounts. This not only drives better digital experiences but also reduces the load on mainframes and back-end systems. By implementing a distributed system leveraging serverless technologies, HSBC was able to achieve their objective of better customer experience.


Lessons Learned

The lessons learned include:

  • Importance of properly setting the shard sizes and batch sizes in Kinesis data streams: By setting the shard sizes appropriately, you can ensure a balanced load distribution and avoid bottlenecks in processing. Similarly, setting the batch sizes correctly can improve throughput and reduce overhead, leading to better overall performance of the system.

  • Impact of language choice on cold start times for Lambda functions: different languages have different boot times. In the case of Java, there is a cold start time for ENI reuse within the VPC. To alleviate this problem, it is recommended to pre-warm the Lambda function and set the container size to 1GB, which has been found to be the optimum size for performance.

  • Attach Lambda functions to a VPC for controlled internet access: provides a highly controlled way for the functions to connect to the outside world. By attaching the functions to a VPC, the security team can set up security groups and egress rules to control the connections. Additionally, by encapsulating a fleet of proxy servers into a VPC endpoint service, the functions can only access the internet through the approved domains and prevent any unauthorized connections.

  • Use dead letter queue (DLQ) to handle failed records: Ensure that problematic records are removed from the batch and processed separately. By sending the failed records to a DLQ, they can be analyzed and addressed separately, allowing the rest of the batch to continue processing without being blocked. This helps to maintain the overall throughput and performance of the system.

  • Implementation of a private cloud within a public cloud for enhanced security: This limits the blast radius and prevents unauthorized communication with external domains. By creating a separate VPC with proxy servers controlled by the HSBC security team, they can control and configure the domains to which the lambda functions can connect. This architecture ensures that any attempts to initiate connections to unapproved destinations are blocked and logged, providing enhanced security.

Sources

Case Study 2: Standard Chartered Migrates Their Core

Overview

Standard Chartered Bank (SCB) is a British multinational banking and financial services company headquartered in London, England. It operates a network of more than 1,200 branches and outlets across more than 70 countries and employs around 87,000 people. The bank chose to migrate their core banking platform so they could focus on client experience, deploy solutions quicker, and integrate new business models and partners more easily. They chose to start with the migration of their core banking platform, Atlas, to develop their cloud capabilities and set themselves up for future migrations. Atlas is a key transaction processing engine that supports critical banking operations and provides the foundation for important upstream processes.


Strategy / Solution

The migration of Atlas was challenging due to its complexity and integration points. However, the bank saw it as an opportunity to develop its cloud capabilities and set the stage for migrating other applications. The migration involved modernizing the application stack and implementing an event-driven architecture, APIs, and DevOps practices. Security and compliance were key considerations, and the bank used various cloud services to ensure data encryption, auditability, and regulatory compliance. The migration process included schema conversion, code modification, and data migration. The bank also adopted a DevOps approach, automating deployment and adopting a blue-green deployment model.


Cloud Services Used

The cloud service provider Standard Chartered used was AWS (Amazon Web Services). AWS services used include:

  • AWS Key Management Service (KMS): The encryption software was used by the bank to encrypt all data in Atlas. They implemented a bring your own key configuration, allowing the bank to maintain full control over their encryption master keys. This ensured security and compliance with internal policies and regulatory standards.

  • AWS CloudTrail: The API usage tool was used to log all account activities for auditability purposes. The activation of AWS CloudTrail was managed by the group landing zone. This also allowed the bank to ensure compliance with internal policies and regulatory standards.

  • AWS Config: The configuration management tool was used to ensure that the resources deployed for Atlas were compliant with the rules defined at the group level. It helped the bank monitor and audit the activity of their database and ensured that any non-compliant resources would generate an alert and could be automatically blocked. Again, this ensure security and compliance with internal policies and regulatory standards.

  • Amazon RDS (Relational Database Service) with Database Activity Stream (DAS): This was used to monitor and audit the activity in Atlas. DAS provided a near real-time stream of the database activity, including details such as user, session, IP address, SQL request, and number of rows written. SCB used Splunk to analyze these DAS events and detect potential security threats, ensuring compliance with internal policies and regulatory standards.

  • Amazon Aurora Global Database: The database service was used to achieve cross-region disaster recovery. By implementing Aurora Global, Atlas was able to have a high throughput, low replica lag, and fast recovery in the event of a region unavailability. This allowed SCB to ensure the reliability and availability of Atlas across multiple cloud regions, meeting their requirements for minimum downtime and data loss. PostgreSQL read replicas were also used to reduce the load on the primary database.

  • AWS DataSync: This data transfer service was used as part of their migration process for Atlas. DataSync was used to migrate historical data from the on-premises environment to the cloud. It allowed SCB to transfer up to 1.5 terabytes of historical data in advance of the second stage of the migration.

  • AWS Database Migration Service (DMS): This was used to migrate Atlas’s database from DB2 to PostgreSQL. It was used to migrate both historical and remaining data, with the historical data migration taking up to six hours and the remaining data migration taking up to three hours.

  • AWS Auto Scaling Groups: These allowed for horizontal scalability by adjusting the number of instances based on the load. Application load balancers were deployed in front of the Auto Scaling Groups to distribute network traffic to the different instances. This helped improve performance and ensure the system could handle the increased workload on the cloud.

  • Application Load Balancers: These were deployed in front of two auto scaling groups to distribute network traffic to different instances. This helped improve the performance and scalability of the system.

Outcomes

From a business perspective, the migration allowed SCB to deliver innovative product offerings to their customers, such as digital banking and banking as a service. It also enabled them to focus on client explerience and deploy solutions quicker. From a technical perspective, the migration improved performance, scalability, and availability of the core banking system, allowing it to sustain up to 10 times more transactions per second and achieve a minimum availability of 99.99%. The migration of Atlas to the cloud enabled SCB to achieve high availability, data regulation compliance, and improved performance.


Lessons Learned

The lessons learned from the migration of SCB’s core banking system to the cloud include:

  • Design for speed and performance: Atlas needed to sustain up to 4,000 transactions per second, which was 10 times more than the previous on-premises system. To achieve this, the architecture of the system was modified to include horizontal scalability using auto scaling groups, application load balancers, and in-memory caching. These changes allowed Atlas to deliver virtual scalability and performance.

  • Ensure high resiliency and availability: By leveraging cloud capabilities such as deploying the application across multiple availability zones and using automatic failover mechanisms, SCB was able to guarantee uninterrupted operations even in the event of a cloud availability zone failure.

  • Leverage the CSP’s expertise and tools: This allowed SCB to accelerate their delivery and avoid preventable pitfalls during their cloud migration journey. By using the CSP’s native tools, they were able to design for speed and performance, ensure high resiliency and availability, and address regulatory compliance challenges.

  • Adopt a Progressive Delivery Model: They adopted a two-step approach to their migration. This allowed them to accelerate their cloud migration journey while still supporting their on-premises deployments in markets where cloud deployments were not allowed by regulatory bodies. This also allowed them to continue enhancing the core banking platform and deploying upgrades to various markets while modernizing the existing stack.

  • Optimizing the technical stack upfront: They optimized the technical stack upfront in order to prepare the application for cloud deployment. By spending the effort to optimize the technical stack, they positioned themselves well to migrate the application to the cloud. This approach allowed them to reduce both change and run costs, optimize the required skills of the development and support teams, and deliver new functionality faster.


Sources

Keep You Head in the Clouds...

Please read this disclaimer.

10 views
bottom of page