logo

Unrestricted access between network segments - RDS - Cloudformation


Need

Restrict access between network segments for RDS instances


Context

  1. Usage of CloudFormation for Infrastructure as Code (IaC)
  2. Usage of AWS::RDS::DBInstance for managing and interacting with AWS RDS database instances

Description

Insecure Code Example

Resources:
  MyDBInstance:
    Type: AWS::RDS::DBInstance
    Properties:
      DBInstanceIdentifier: "mydb"
      AllocatedStorage: 20
      StorageType: "gp2"
      Engine: "mysql"
      EngineVersion: "5.7"
      DBInstanceClass: "db.t2.micro"
      MasterUsername: "foo"
      MasterUserPassword: "foobarbaz"
      PubliclyAccessible: true
      VPCSecurityGroups:
        - !Ref MySecurityGroup

The CloudFormation template below creates a publicly accessible AWS RDS instance without specifying a database subnet group. The `PubliclyAccessible` property is set to `true`, meaning the database instance is exposed to the internet. This is a vulnerability because it allows unrestricted access between network segments. Any public or private subnet can connect to the RDS instance without any restrictions. This could potentially lead to unauthorized access to sensitive data stored in the database. Additionally, the lack of a defined database subnet group means that the RDS instance is not associated with any specific subnets. This could lead to issues with network routing and access control. To mitigate this, a database subnet group should be explicitly defined, and the `PubliclyAccessible` attribute should be set to `false` to ensure that the instance is not publicly exposed.

Steps

  1. Create a Database Subnet Group in your AWS account.
  2. Specify the Database Subnet Group in the RDS resource configuration.
  3. Ensure that the RDS instance is not publicly accessible.
  4. Review and update the security group rules to restrict access to the RDS instance.

Secure Code Example

Resources:
  MyDBSubnetGroup:
    Type: AWS::RDS::DBSubnetGroup
    Properties:
      DBSubnetGroupDescription: "Database subnet group"
      SubnetIds:
        - subnet-xxxxxxxx
        - subnet-yyyyyyyy

  MySecurityGroup:
    Type: AWS::EC2::SecurityGroup
    Properties:
      GroupDescription: "Restricted DB access"
      VpcId: vpc-xxxxxxxx
      SecurityGroupIngress:
        - IpProtocol: "tcp"
          FromPort: 3306
          ToPort: 3306
          CidrIp: "10.0.0.0/16"  # Restricting access to internal network

  MyDBInstance:
    Type: AWS::RDS::DBInstance
    Properties:
      DBInstanceIdentifier: "mydb"
      AllocatedStorage: 20
      StorageType: "gp2"
      Engine: "mysql"
      EngineVersion: "5.7"
      DBInstanceClass: "db.t2.micro"
      MasterUsername: "foo"
      MasterUserPassword: "foobarbaz"
      PubliclyAccessible: false
      VPCSecurityGroups:
        - !Ref MySecurityGroup
      DBSubnetGroupName: !Ref MyDBSubnetGroup

The CloudFormation template below creates a Database Subnet Group using the `AWS::RDS::DBSubnetGroup` resource, specifying the subnets that should be used. Then, it creates an RDS instance with the `PubliclyAccessible` property set to `false`, ensuring that the database instance is not publicly accessible. The `DBSubnetGroupName` property references the previously created database subnet group, ensuring that the RDS instance is placed within a controlled network environment. Additionally, a security group is defined to restrict inbound access, ensuring that only authorized internal network segments can reach the database.


References

  • 109 - Unrestricted access between network segments - RDS

  • Last updated

    2025/04/03