diff --git a/CHANGELOG.md b/CHANGELOG.md
index e24ecc0a2d2..f57e65a2ee7 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -145,6 +145,7 @@ Ansible Changes By Release
   * ios_system
   * ios_vrf
 - iosxr_system
+- iso_extract
 - jenkins_script
 - ldap:
   * ldap_attr
diff --git a/lib/ansible/modules/files/iso_extract.py b/lib/ansible/modules/files/iso_extract.py
new file mode 100644
index 00000000000..a72089e049b
--- /dev/null
+++ b/lib/ansible/modules/files/iso_extract.py
@@ -0,0 +1,130 @@
+#!/usr/bin/python
+# -*- coding: utf-8 -*-
+
+# (c) 2013, Jeroen Hoekx <jeroen.hoekx@dsquare.be>
+# (c) 2016, Matt Robinson <git@nerdoftheherd.com>
+#
+# This file is part of Ansible
+#
+# Ansible is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 3 of the License, or
+# (at your option) any later version.
+#
+# Ansible is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with Ansible.  If not, see <http://www.gnu.org/licenses/>.
+
+ANSIBLE_METADATA = {'status': ['preview'],
+                    'supported_by': 'core',
+                    'version': '1.0'}
+
+DOCUMENTATION = r'''
+---
+author:
+- Jeroen Hoekx (@jhoekx)
+- Matt Robinson (@ribbons)
+module: iso_extract
+short_description: Extract files from an ISO image.
+description:
+- This module mounts an iso image in a temporary directory and extracts
+  files from there to a given destination.
+version_added: "2.3"
+options:
+  image:
+    description:
+    - The ISO image to extract files from.
+    required: true
+    aliases: ['path', 'src']
+  dest:
+    description:
+    - The destination directory to extract files to.
+    required: true
+  files:
+    description:
+    - A list of files to extract from the image.
+    - Extracting directories does not work.
+    required: true
+notes:
+- Only the file hash (content) is taken into account for extracting files
+  from the ISO image.
+'''
+
+EXAMPLES = r'''
+- name: Extract kernel and ramdisk from a LiveCD
+  iso_extract:
+    image: /tmp/rear-test.iso
+    dest: /tmp/virt-rear/
+    files:
+    - isolinux/kernel
+    - isolinux/initrd.cgz
+'''
+
+RETURN = r'''
+#
+'''
+
+import os
+import shutil
+import tempfile
+
+from ansible.module_utils.basic import AnsibleModule
+from ansible.module_utils.pycompat24 import get_exception
+
+def main():
+    module = AnsibleModule(
+        argument_spec = dict(
+            image = dict(required=True, type='path', aliases=['path', 'src']),
+            dest = dict(required=True, type='path'),
+            files = dict(required=True, type='list'),
+        ),
+        supports_check_mode = True,
+    )
+    image = module.params['image']
+    dest = module.params['dest']
+    files = module.params['files']
+
+    changed = False
+
+    if not os.path.exists(dest):
+        module.fail_json(msg='Directory "%s" does not exist' % dest)
+
+    if not os.path.exists(os.path.dirname(image)):
+        module.fail_json(msg='ISO image "%s" does not exist' % image)
+
+    tmp_dir = tempfile.mkdtemp()
+    rc, out, err = module.run_command('mount -o loop,ro "%s" "%s"' % (image, tmp_dir))
+    if rc != 0:
+        os.rmdir(tmp_dir)
+        module.fail_json(msg='Failed to mount ISO image "%s"' % image)
+
+    e = None
+    try:
+        for file in files:
+            tmp_src = os.path.join(tmp_dir, file)
+            src_hash = module.sha1(tmp_src)
+
+            dest_file = os.path.join(dest, os.path.basename(file))
+
+            if os.path.exists(dest_file):
+                dest_hash = module.sha1(dest_file)
+            else:
+                dest_hash = None
+
+            if src_hash != dest_hash:
+                if not module.check_mode:
+                    shutil.copy(tmp_src, dest_file)
+
+                changed = True
+    finally:
+        module.run_command('umount "%s"' % tmp_dir)
+        os.rmdir(tmp_dir)
+
+    module.exit_json(changed=changed)
+
+if __name__ == '__main__':
+    main()