# Copyright (c) 2012 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

{
  'variables': {
    'nw_product_name': 'node-webkit',
  },
  'targets': [
    {
      'target_name': 'nw_lib',
      'type': 'static_library',
      'defines!': ['CONTENT_IMPLEMENTATION'],
      'variables': {
        'chromium_code': 1,
      },
      'dependencies': [
        '<(DEPTH)/base/base.gyp:base',
        '<(DEPTH)/base/third_party/dynamic_annotations/dynamic_annotations.gyp:dynamic_annotations',
        '<(DEPTH)/components/components.gyp:autofill_content_renderer',
        '<(DEPTH)/components/components.gyp:browser_context_keyed_service',
        '<(DEPTH)/content/content.gyp:content_app_browser',
        '<(DEPTH)/content/content.gyp:content_browser',
        '<(DEPTH)/content/content.gyp:content_common',
        '<(DEPTH)/content/content.gyp:content_gpu',
        '<(DEPTH)/content/content.gyp:content_plugin',
        '<(DEPTH)/content/content.gyp:content_ppapi_plugin',
        '<(DEPTH)/content/content.gyp:content_renderer',
        '<(DEPTH)/content/content.gyp:content_utility',
        '<(DEPTH)/content/content.gyp:content_worker',
        '<(DEPTH)/content/content_resources.gyp:content_resources',
        '<(DEPTH)/ipc/ipc.gyp:ipc',
        '<(DEPTH)/media/media.gyp:media',
        '<(DEPTH)/net/net.gyp:net_with_v8',
        '<(DEPTH)/net/net.gyp:net_resources',
        '<(DEPTH)/printing/printing.gyp:printing',
        '<(DEPTH)/skia/skia.gyp:skia',
        '<(DEPTH)/third_party/node/node.gyp:node',
        '<(DEPTH)/ui/ui.gyp:ui',
        '<(DEPTH)/ui/ui.gyp:ui_resources',
        '<(DEPTH)/url/url.gyp:url_lib',
        '<(DEPTH)/v8/tools/gyp/v8.gyp:v8',
        '<(DEPTH)/webkit/support/webkit_support.gyp:webkit_support',
        '<(DEPTH)/third_party/zlib/zlib.gyp:minizip',
        '<(DEPTH)/third_party/WebKit/public/blink.gyp:blink',
        'nw_resources',
      ],
      'include_dirs': [
        '<(DEPTH)',
        '<(DEPTH)/third_party/WebKit/Source',
        '<(DEPTH)/third_party/WebKit/public/web',
        '<(DEPTH)/breakpad/src',
        '<(SHARED_INTERMEDIATE_DIR)/blink',
        '<(SHARED_INTERMEDIATE_DIR)/blink/bindings',
      ],
      'cflags_cc': [
        '-Wno-error=c++0x-compat',
      ],
      'sources': [
        '<(DEPTH)/chrome/browser/chrome_process_finder_win.cc',
        '<(DEPTH)/chrome/browser/chrome_process_finder_win.h',
        '<(DEPTH)/chrome/common/child_process_logging.h',
        '<(DEPTH)/chrome/common/child_process_logging_mac.mm',
        '<(DEPTH)/chrome/common/child_process_logging_posix.cc',
        '<(DEPTH)/chrome/common/child_process_logging_win.cc',
        '<(DEPTH)/chrome/common/crash_keys.cc',
        '<(DEPTH)/chrome/common/dump_without_crashing.cc',
        '<(DEPTH)/chrome/common/env_vars.cc',
        '<(DEPTH)/chrome/browser/crash_upload_list.cc',
        '<(DEPTH)/chrome/browser/upload_list.cc',
        '<(DEPTH)/chrome/browser/platform_util_common_linux.cc',
        '<(DEPTH)/chrome/browser/platform_util_linux.cc',
        '<(DEPTH)/chrome/browser/platform_util_mac.mm',
        '<(DEPTH)/chrome/browser/platform_util_win.cc',
        '<(DEPTH)/chrome/browser/platform_util.h',
        '<(DEPTH)/chrome/browser/process_singleton_linux.cc',
        '<(DEPTH)/chrome/browser/process_singleton_mac.cc',
        '<(DEPTH)/chrome/browser/process_singleton_win.cc',
        '<(DEPTH)/chrome/browser/process_singleton.h',
        '<(DEPTH)/chrome/browser/status_icons/status_icon.cc',
        '<(DEPTH)/chrome/browser/status_icons/status_icon.h',
        '<(DEPTH)/chrome/browser/status_icons/status_icon_observer.h',
        '<(DEPTH)/chrome/browser/status_icons/status_tray.cc',
        '<(DEPTH)/chrome/browser/status_icons/status_tray.h',
        '<(DEPTH)/chrome/browser/ui/cocoa/custom_frame_view.h',
        '<(DEPTH)/chrome/browser/ui/cocoa/custom_frame_view.mm',
        '<(DEPTH)/chrome/browser/ui/base_window.h',
        '<(DEPTH)/chrome/browser/ui/gtk/gtk_window_util.cc',
        '<(DEPTH)/chrome/browser/ui/gtk/gtk_window_util.h',
        '<(DEPTH)/chrome/browser/ui/views/status_icons/status_icon_win.cc',
        '<(DEPTH)/chrome/browser/ui/views/status_icons/status_icon_win.h',
        '<(DEPTH)/chrome/browser/ui/views/status_icons/status_tray_win.cc',
        '<(DEPTH)/chrome/browser/ui/views/status_icons/status_tray_win.h',
        '<(DEPTH)/chrome/common/chrome_constants.cc',
        '<(DEPTH)/chrome/common/chrome_constants.h',
        '<(DEPTH)/chrome/common/chrome_switches.cc',
        '<(DEPTH)/chrome/common/chrome_switches.h',
        '<(DEPTH)/extensions/common/draggable_region.cc',
        '<(DEPTH)/extensions/common/draggable_region.h',
        '<(DEPTH)/third_party/zlib/google/zip.cc',
        '<(DEPTH)/third_party/zlib/google/zip.h',
        '<(DEPTH)/third_party/zlib/google/zip_reader.cc',
        '<(DEPTH)/third_party/zlib/google/zip_reader.h',
        '<(DEPTH)/third_party/zlib/google/zip_internal.cc',
        '<(DEPTH)/third_party/zlib/google/zip_internal.h',
        '<(DEPTH)/components/autofill/content/renderer/page_click_listener.h',
        '<(DEPTH)/components/autofill/content/renderer/page_click_tracker.cc',
        '<(DEPTH)/components/autofill/content/renderer/page_click_tracker.h',
        '<(DEPTH)/chrome/renderer/static_v8_external_string_resource.cc',
        '<(DEPTH)/chrome/renderer/static_v8_external_string_resource.h',
        'src/api/api_messages.cc',
        'src/api/api_messages.h',
        'src/api/app/app.cc',
        'src/api/app/app.h',
        'src/api/bindings_common.cc',
        'src/api/bindings_common.h',
        'src/api/base/base.cc',
        'src/api/base/base.h',
        'src/api/clipboard/clipboard.cc',
        'src/api/clipboard/clipboard.h',
        'src/api/dispatcher.cc',
        'src/api/dispatcher.h',
        'src/api/dispatcher_bindings.cc',
        'src/api/dispatcher_bindings.h',
        'src/api/dispatcher_host.cc',
        'src/api/dispatcher_host.h',
        'src/api/window_bindings.cc',
        'src/api/window_bindings.h',
        'src/api/menu/menu.cc',
        'src/api/menu/menu.h',
        'src/api/menu/menu_delegate_win.cc',
        'src/api/menu/menu_delegate_win.h',
        'src/api/menu/menu_gtk.cc',
        'src/api/menu/menu_mac.mm',
        'src/api/menu/menu_win.cc',
        'src/api/menuitem/menuitem.cc',
        'src/api/menuitem/menuitem.h',
        'src/api/menuitem/menuitem_gtk.cc',
        'src/api/menuitem/menuitem_mac.mm',
        'src/api/menuitem/menuitem_win.cc',
        'src/api/menuitem/menuitem_delegate_mac.h',
        'src/api/menuitem/menuitem_delegate_mac.mm',
        'src/api/shell/shell.cc',
        'src/api/shell/shell.h',
        'src/api/tray/tray.cc',
        'src/api/tray/tray.h',
        'src/api/tray/tray_gtk.cc',
        'src/api/tray/tray_mac.mm',
        'src/api/tray/tray_win.cc',
        'src/api/window/window.cc',
        'src/api/window/window.h',
        'src/browser/app_controller_mac.h',
        'src/browser/app_controller_mac.mm',
        'src/browser/capture_page_helper.h',
        'src/browser/capture_page_helper.cc',
        'src/browser/color_chooser_gtk.cc',
        'src/browser/color_chooser_win.cc',
        'src/browser/color_chooser_mac.mm',
        'src/browser/chrome_event_processing_window.mm',
        'src/browser/chrome_event_processing_window.h',
        'src/browser/file_select_helper.cc',
        'src/browser/file_select_helper.h',
        'src/browser/native_window.cc',
        'src/browser/native_window.h',
        'src/browser/native_window_gtk.cc',
        'src/browser/native_window_gtk.h',
        'src/browser/native_window_helper_mac.h',
        'src/browser/native_window_mac.h',
        'src/browser/native_window_mac.mm',
        'src/browser/native_window_toolbar_win.cc',
        'src/browser/native_window_toolbar_win.h',
        'src/browser/native_window_win.cc',
        'src/browser/native_window_win.h',
        'src/browser/net_disk_cache_remover.cc',
        'src/browser/net_disk_cache_remover.h',
        'src/browser/printing/print_dialog_gtk.cc',
        'src/browser/printing/print_dialog_gtk.h',
        'src/browser/printing/print_job.cc',
        'src/browser/printing/print_job.h',
        'src/browser/printing/print_job_manager.cc',
        'src/browser/printing/print_job_manager.h',
        'src/browser/printing/print_job_worker.cc',
        'src/browser/printing/print_job_worker.h',
        'src/browser/printing/print_job_worker_owner.h',
        'src/browser/printing/printing_message_filter.cc',
        'src/browser/printing/printing_message_filter.h',
        'src/browser/printing/printer_query.cc',
        'src/browser/printing/printer_query.h',
        'src/browser/printing/print_view_manager.cc',
        'src/browser/printing/print_view_manager.h',
        'src/browser/shell_application_mac.h',
        'src/browser/shell_application_mac.mm',
        'src/browser/shell_devtools_delegate.cc',
        'src/browser/shell_devtools_delegate.h',
        'src/browser/shell_download_manager_delegate.cc',
        'src/browser/shell_download_manager_delegate.h',
        'src/browser/shell_download_manager_delegate_win.cc',
        'src/browser/shell_download_manager_delegate_gtk.cc',
        'src/browser/shell_download_manager_delegate_mac.mm',
        'src/browser/shell_javascript_dialog_creator.cc',
        'src/browser/shell_javascript_dialog_creator.h',
        'src/browser/shell_javascript_dialog_gtk.cc',
        'src/browser/shell_javascript_dialog_mac.mm',
        'src/browser/shell_javascript_dialog_win.cc',
        'src/browser/shell_javascript_dialog.h',
        'src/browser/shell_login_dialog_gtk.cc',
        'src/browser/shell_login_dialog_mac.mm',
        'src/browser/shell_login_dialog_win.cc',
        'src/browser/shell_login_dialog.cc',
        'src/browser/shell_login_dialog.h',
        'src/browser/shell_resource_dispatcher_host_delegate.cc',
        'src/browser/shell_resource_dispatcher_host_delegate.h',
        'src/browser/shell_toolbar_delegate_mac.h',
        'src/browser/shell_toolbar_delegate_mac.mm',
        'src/browser/standard_menus_mac.h',
        'src/browser/standard_menus_mac.mm',
        'src/chrome_breakpad_client.cc',
        'src/chrome_breakpad_client.h',
        'src/chrome_breakpad_client_mac.mm',
        'src/common/print_messages.cc',
        'src/common/print_messages.h',
        'src/common/shell_switches.cc',
        'src/common/shell_switches.h',
        'src/breakpad_linux_impl.h',
        'src/breakpad_mac.mm',
        'src/breakpad_mac.h',
        'src/breakpad_win.cc',
        'src/breakpad_win.h',
        'src/hard_error_handler_win.cc',
        'src/hard_error_handler_win.h',
        'src/geolocation/shell_access_token_store.cc',
        'src/geolocation/shell_access_token_store.h',
        'src/media/media_internals.cc',
        'src/media/media_internals.h',
        'src/media/media_capture_devices_dispatcher.cc',
        'src/media/media_capture_devices_dispatcher.h',
        'src/media/media_stream_devices_controller.cc',
        'src/media/media_stream_devices_controller.h',
        'src/net/app_protocol_handler.cc',
        'src/net/app_protocol_handler.h',
        'src/net/clear_on_exit_policy.h',
        'src/net/clear_on_exit_policy.cc',
        'src/net/resource_request_job.cc',
        'src/net/resource_request_job.h',
        'src/net/shell_network_delegate.cc',
        'src/net/shell_network_delegate.h',
        'src/net/shell_url_request_context_getter.cc',
        'src/net/shell_url_request_context_getter.h',
        'src/nw_protocol_handler.cc',
        'src/nw_protocol_handler.h',
        'src/nw_package.cc',
        'src/nw_package.h',
        'src/nw_version.h',
        'src/paths_mac.h',
        'src/paths_mac.mm',
        'src/renderer/common/render_messages.cc',
        'src/renderer/common/render_messages.h',
        'src/renderer/prerenderer/prerenderer_client.cc',
        'src/renderer/prerenderer/prerenderer_client.h',
        'src/renderer/printing/print_web_view_helper.cc',
        'src/renderer/printing/print_web_view_helper.h',
        'src/renderer/printing/print_web_view_helper_linux.cc',
        'src/renderer/printing/print_web_view_helper_mac.mm',
        'src/renderer/printing/print_web_view_helper_win.cc',
        'src/renderer/nw_render_view_observer.cc',
        'src/renderer/nw_render_view_observer.h',
        'src/renderer/shell_content_renderer_client.cc',
        'src/renderer/shell_content_renderer_client.h',
        'src/renderer/shell_render_process_observer.cc',
        'src/renderer/shell_render_process_observer.h',
        'src/nw_shell.cc',
        'src/nw_shell.h',
        'src/shell_browser_context.cc',
        'src/shell_browser_context.h',
        'src/shell_browser_main.cc',
        'src/shell_browser_main.h',
        'src/shell_browser_main_parts.cc',
        'src/shell_browser_main_parts.h',
        'src/shell_browser_main_parts_mac.mm',
        'src/shell_content_browser_client.cc',
        'src/shell_content_browser_client.h',
        'src/shell_content_client.cc',
        'src/shell_content_client.h',
        'src/shell_main_delegate.cc',
        'src/shell_main_delegate.h',
      ],
      'msvs_settings': {
        'VCLinkerTool': {
          'SubSystem': '2',  # Set /SUBSYSTEM:WINDOWS
        },
      },
      'conditions': [
        ['OS=="win" and win_use_allocator_shim==1', {
          'dependencies': [
            '<(DEPTH)/base/allocator/allocator.gyp:allocator',
          ],
        }],
        ['(os_posix==1 and OS != "mac" and linux_use_tcmalloc==1)', {
          'dependencies': [
            # This is needed by content/app/content_main_runner.cc
            '<(DEPTH)/base/allocator/allocator.gyp:allocator',
          ],
        }],
        ['OS=="win"', {
          'dependencies': [
            '<(DEPTH)/breakpad/breakpad.gyp:breakpad_handler',
            '<(DEPTH)/breakpad/breakpad.gyp:breakpad_sender',
            '<(DEPTH)/components/components.gyp:breakpad_component',
          ],
        }],
        ['os_posix==1 and OS != "mac" and OS != "ios"', {
          'sources': [
            'src/breakpad_linux.cc',
            'src/breakpad_linux.h',
            'src/crash_handler_host_linux.cc',
            'src/crash_handler_host_linux.h',
          ],
          'dependencies': [
            '<(DEPTH)/breakpad/breakpad.gyp:breakpad_client',
            '<(DEPTH)/components/components.gyp:breakpad_component',
          ],
        }],
        ['OS == "mac"', {
          'sources!': [
            '<(DEPTH)/chrome/common/child_process_logging_posix.cc',
          ],
          'dependencies': [
            '<(DEPTH)/breakpad/breakpad.gyp:breakpad',
            '<(DEPTH)/components/components.gyp:breakpad_component',
          ],
        }],
        ['toolkit_uses_gtk == 1', {
          'dependencies': [
            # For FT_Init_FreeType and friends.
            '../build/linux/system.gyp:freetype2',
            '../build/linux/system.gyp:gtk',
            '../build/linux/system.gyp:gtkprint',
          ],
        }],
        ['OS=="win"', {
          'sources': [
            'src/browser/color_chooser_dialog.cc',
            'src/browser/color_chooser_dialog.h',
          ],
          'resource_include_dirs': [
            '<(SHARED_INTERMEDIATE_DIR)/webkit',
          ],
          'dependencies': [
            '<(DEPTH)/ui/ui.gyp:ui_resources',
            '<(DEPTH)/ui/views/controls/webview/webview.gyp:webview',
            '<(DEPTH)/ui/views/views.gyp:views',
            '<(DEPTH)/webkit/webkit_resources.gyp:webkit_resources',
            '<(DEPTH)/webkit/webkit_resources.gyp:webkit_strings',
          ],
          'configurations': {
            'Debug_Base': {
              'msvs_settings': {
                'VCLinkerTool': {
                  'LinkIncremental': '<(msvs_large_module_debug_link_mode)',
                },
              },
            },
          },
          'msvs_disabled_warnings': [ 4800 ],
        }],  # OS=="win"
      ],
    },
    {
      'target_name': 'nw_resources',
      'type': 'none',
      'dependencies': [
        'generate_nw_resources',
        'about_credits',
      ],
      'variables': {
        'grit_out_dir': '<(SHARED_INTERMEDIATE_DIR)/content',
      },
      'includes': [ '../../build/grit_target.gypi' ],
      'copies': [
        {
          'destination': '<(PRODUCT_DIR)',
          'files': [
            '<(SHARED_INTERMEDIATE_DIR)/content/nw_resources.pak'
          ],
        },
      ],
    },
    {
      'target_name': 'generate_nw_resources',
      'type': 'none',
      'variables': {
        'grit_out_dir': '<(SHARED_INTERMEDIATE_DIR)/content',
      },
      'actions': [
        {
          'action_name': 'nw_resources',
          'variables': {
            'grit_grd_file': 'src/resources/nw_resources.grd',
          },
          'includes': [ '../../build/grit_action.gypi' ],
        },
      ],
    },
    {
      'target_name': 'about_credits',
      'type': 'none',
      'actions': [
        {
          'variables': {
            'generator_path': '../../tools/licenses.py',
            'about_credits_file': '<(PRODUCT_DIR)/credits.html',
          },
          'action_name': 'generate_about_credits',
          'inputs': [
            # TODO(phajdan.jr): make licenses.py print inputs too.
            '<(generator_path)',
          ],
          'outputs': [
            '<(about_credits_file)',
          ],
          'hard_dependency': 1,
          'action': ['python',
                     '<(generator_path)',
                     'credits',
                     '<(about_credits_file)',
          ],
          'message': 'Generating about:credits.',
        },
      ],
    },
    {
      # We build a minimal set of resources so WebKit in nw has
      # access to necessary resources.
      'target_name': 'nw_pak',
      'type': 'none',
      'dependencies': [
        '<(DEPTH)/content/browser/devtools/devtools_resources.gyp:devtools_resources',
        '<(DEPTH)/ui/ui.gyp:ui_resources',
        'nw_resources',
      ],
      'variables': {
        'repack_path': '<(DEPTH)/tools/grit/grit/format/repack.py',
      },
      'actions': [
        {
          'action_name': 'repack_nw_pack',
          'variables': {
            'pak_inputs': [
              '<(SHARED_INTERMEDIATE_DIR)/content/content_resources.pak',
              '<(SHARED_INTERMEDIATE_DIR)/content/nw_resources.pak',
              '<(SHARED_INTERMEDIATE_DIR)/net/net_resources.pak',
              '<(SHARED_INTERMEDIATE_DIR)/ui/app_locale_settings/app_locale_settings_en-US.pak',
              '<(SHARED_INTERMEDIATE_DIR)/ui/ui_resources/ui_resources_100_percent.pak',
              '<(SHARED_INTERMEDIATE_DIR)/ui/ui_strings/ui_strings_en-US.pak',
              '<(SHARED_INTERMEDIATE_DIR)/webkit/devtools_resources.pak',
              #'<(SHARED_INTERMEDIATE_DIR)/webkit/webkit_chromium_resources.pak',
              '<(SHARED_INTERMEDIATE_DIR)/webkit/webkit_resources_100_percent.pak',
              '<(SHARED_INTERMEDIATE_DIR)/webkit/webkit_strings_en-US.pak',
            ],
          },
          'inputs': [
            '<(repack_path)',
            '<@(pak_inputs)',
          ],
          'outputs': [
            '<(PRODUCT_DIR)/nw.pak',
          ],
          'action': ['python', '<(repack_path)', '<@(_outputs)',
                     '<@(pak_inputs)'],
        },
      ],
    },
    {
      'target_name': 'strip',
      'type': 'none',
      'actions': [
        {
          'action_name': 'strip_nw_binaries',
          'inputs': [
            '<(PRODUCT_DIR)/nw',
          ],
          'outputs': [
            '<(PRODUCT_DIR)/strip_nw.stamp',
          ],
          'action': ['strip',
                     '<@(_inputs)'],
          'message': 'Stripping release executable',
        },
      ],
      'dependencies': [
        'nw',
      ],
    },
    {
      'target_name': 'dist',
      'type': 'none',
      'actions': [
        {
          'action_name': 'package_nw_binaries',
          'variables':{
            'package_script': '<(DEPTH)/content/nw/tools/package_binaries.py',
          },
          'inputs': [
            '<(package_script)',
          ],
          'outputs':[
            '<(PRODUCT_DIR)/new_package.re',
          ],
          'action': ['python', '<(package_script)'],
        },
      ],
      'dependencies': [
        '<(DEPTH)/chrome/chrome.gyp:chromedriver2_server',
      ],
      'conditions': [
        ['OS == "linux"', {
          'dependencies': [
            'strip',
          ],
        }],
      ],
    },
    {
      'target_name': 'nw',
      'type': 'executable',
      'mac_bundle': 1,
      'defines!': ['CONTENT_IMPLEMENTATION'],
      'variables': {
        'chromium_code': 1,
      },
      'dependencies': [
        'nw_lib',
        'nw_pak',
      ],
      'include_dirs': [
        '<(DEPTH)',
      ],
      'sources': [
        '../app/startup_helper_win.cc',
        'src/shell_main.cc',
      ],
      'mac_bundle_resources': [
        'src/mac/nw.icns',
        'src/mac/app-Info.plist',
      ],
      # TODO(mark): Come up with a fancier way to do this.  It should only
      # be necessary to list app-Info.plist once, not the three times it is
      # listed here.
      'mac_bundle_resources!': [
        'src/mac/app-Info.plist',
      ],
      'xcode_settings': {
        'INFOPLIST_FILE': 'nw/src/mac/app-Info.plist',
      },
      'msvs_settings': {
        'VCLinkerTool': {
          'SubSystem': '2',  # Set /SUBSYSTEM:WINDOWS
        },
      },
      'conditions': [
        ['OS=="win" and win_use_allocator_shim==1', {
          'dependencies': [
            '<(DEPTH)/base/allocator/allocator.gyp:allocator',
          ],
        }],
        ['OS=="win"', {
          'sources': [
            'src/shell.rc',
            '<(SHARED_INTERMEDIATE_DIR)/ui/ui_resources/ui_unscaled_resources.rc',
          ],
          'configurations': {
            'Debug_Base': {
              'msvs_settings': {
                'VCLinkerTool': {
                  'LinkIncremental': '<(msvs_large_module_debug_link_mode)',
                },
              },
            },
          },
        }],  # OS=="win"
        ['OS == "win" or toolkit_uses_gtk == 1', {
          'dependencies': [
            '<(DEPTH)/sandbox/sandbox.gyp:sandbox',
          ],
        }],  # OS=="win" or (toolkit_uses_gtk == 1 and selinux == 0)
        ['toolkit_uses_gtk == 1', {
          'dependencies': [
            '<(DEPTH)/build/linux/system.gyp:gtk',
          ],
        }],  # toolkit_uses_gtk
        ['OS=="mac"', {
          'product_name': '<(nw_product_name)',
          'dependencies!': [
            'nw_lib',
          ],
          'dependencies': [
            'nw_framework',
            'nw_helper_app',
          ],
          'copies': [
            {
              'destination': '<(PRODUCT_DIR)/<(nw_product_name).app/Contents/Frameworks',
              'files': [
                '<(PRODUCT_DIR)/<(nw_product_name) Helper.app',
                '<(PRODUCT_DIR)/crash_inspector',
              ],
            },
          ],
          'postbuilds': [
            {
              'postbuild_name': 'Copy <(nw_product_name) Framework.framework',
              'action': [
                '<(DEPTH)/build/mac/copy_framework_unversioned.sh',
                '${BUILT_PRODUCTS_DIR}/<(nw_product_name) Framework.framework',
                '${BUILT_PRODUCTS_DIR}/${CONTENTS_FOLDER_PATH}/Frameworks',
              ],
            },
            {
              'postbuild_name': 'Fix Framework Link',
              'action': [
                'install_name_tool',
                '-change',
                '/Library/Frameworks/<(nw_product_name) Framework.framework/Versions/A/<(nw_product_name) Framework',
                '@executable_path/../Frameworks/<(nw_product_name) Framework.framework/<(nw_product_name) Framework',
                '${BUILT_PRODUCTS_DIR}/${EXECUTABLE_PATH}'
              ],
            },
            {
              # Modify the Info.plist as needed.
              'postbuild_name': 'Tweak Info.plist',
              'action': ['<(DEPTH)/build/mac/tweak_info_plist.py',
                         '--breakpad=0',
                         '--keystone=0'],
            },
            {
              # This postbuid step is responsible for creating the following
              # helpers:
              #
              # Content Shell Helper EH.app and Content Shell Helper NP.app are
              # created from Content Shell Helper.app.
              #
              # The EH helper is marked for an executable heap. The NP helper
              # is marked for no PIE (ASLR).
              'postbuild_name': 'Make More Helpers',
              'action': [
                '<(DEPTH)/build/mac/make_more_helpers.sh',
                'Frameworks',
                '<(nw_product_name)',
              ],
            },
            {
              # Make sure there isn't any Objective-C in the shell's
              # executable.
              'postbuild_name': 'Verify No Objective-C',
              'action': [
                '<(DEPTH)/build/mac/verify_no_objc.sh',
              ],
            },
          ],
        }],  # OS=="mac"
      ],
    },
  ],
  'conditions': [
    ['OS=="mac"', {
      'targets': [
        {
          'target_name': 'nw_framework',
          'type': 'shared_library',
          'product_name': '<(nw_product_name) Framework',
          'mac_bundle': 1,
          'mac_bundle_resources': [
            'src/mac/English.lproj/HttpAuth.xib',
            '<(PRODUCT_DIR)/nw.pak'
          ],
          'dependencies': [
            'nw_lib',
          ],
          'include_dirs': [
            '../..',
          ],
          'sources': [
            'src/shell_content_main.cc',
            'src/shell_content_main.h',
          ],
          'copies': [
            {
              # Copy FFmpeg binaries for audio/video support.
              'destination': '<(PRODUCT_DIR)/$(CONTENTS_FOLDER_PATH)/Libraries',
              'files': [
                '<(PRODUCT_DIR)/ffmpegsumo.so',
              ],
            },
          ],
        },  # target nw_framework
        {
          'target_name': 'nw_helper_app',
          'type': 'executable',
          'variables': { 'enable_wexit_time_destructors': 1, },
          'product_name': '<(nw_product_name) Helper',
          'mac_bundle': 1,
          'dependencies': [
            'nw_framework',
          ],
          'sources': [
            'src/shell_main.cc',
            'src/mac/helper-Info.plist',
          ],
          # TODO(mark): Come up with a fancier way to do this.  It should only
          # be necessary to list helper-Info.plist once, not the three times it
          # is listed here.
          'mac_bundle_resources!': [
            'src/mac/helper-Info.plist',
          ],
          # TODO(mark): For now, don't put any resources into this app.  Its
          # resources directory will be a symbolic link to the browser app's
          # resources directory.
          'mac_bundle_resources/': [
            ['exclude', '.*'],
          ],
          'xcode_settings': {
            'INFOPLIST_FILE': 'nw/src/mac/helper-Info.plist',
          },
          'postbuilds': [
            {
              # The framework defines its load-time path
              # (DYLIB_INSTALL_NAME_BASE) relative to the main executable
              # (chrome).  A different relative path needs to be used in
              # nw_helper_app.
              'postbuild_name': 'Fix Framework Link',
              'action': [
                'install_name_tool',
                '-change',
                '/Library/Frameworks/<(nw_product_name) Framework.framework/Versions/A/<(nw_product_name) Framework',
                '@executable_path/../../../../Frameworks/<(nw_product_name) Framework.framework/<(nw_product_name) Framework',
                '${BUILT_PRODUCTS_DIR}/${EXECUTABLE_PATH}'
              ],
            },
            {
              # Modify the Info.plist as needed.  The script explains why this
              # is needed.  This is also done in the chrome and chrome_dll
              # targets.  In this case, --breakpad=0, --keystone=0, and --svn=0
              # are used because Breakpad, Keystone, and Subversion keys are
              # never placed into the helper.
              'postbuild_name': 'Tweak Info.plist',
              'action': ['<(DEPTH)/build/mac/tweak_info_plist.py',
                         '--breakpad=0',
                         '--keystone=0'],
            },
            {
              # Make sure there isn't any Objective-C in the helper app's
              # executable.
              'postbuild_name': 'Verify No Objective-C',
              'action': [
                '<(DEPTH)/build/mac/verify_no_objc.sh',
              ],
            },
          ],
          'conditions': [
            ['component=="shared_library"', {
              'xcode_settings': {
                'LD_RUNPATH_SEARCH_PATHS': [
                  # Get back from Content Shell.app/Contents/Frameworks/
                  #                                 Helper.app/Contents/MacOS
                  '@loader_path/../../../../../..',
                ],
              },
            }],
          ],
        },  # target nw_helper_app
      ],
    }],  # OS=="mac"
    ['OS=="linux"',
      { 'targets': [
        {
          'target_name': 'linux_symbols',
          'type': 'none',
          'conditions': [
            ['linux_dump_symbols==1', {
              'actions': [
                {
                  'action_name': 'dump_symbols',
                  'inputs': [
                    '<(DEPTH)/build/linux/dump_app_syms',
                    '<(PRODUCT_DIR)/dump_syms',
                    '<(PRODUCT_DIR)/nw',
                  ],
                  'outputs': [
                    '<(PRODUCT_DIR)/nw.breakpad.<(target_arch)',
                  ],
                  'action': ['<(DEPTH)/build/linux/dump_app_syms',
                             '<(PRODUCT_DIR)/dump_syms',
                             '<(linux_strip_binary)',
                             '<(PRODUCT_DIR)/nw',
                             '<@(_outputs)'],
                  'message': 'Dumping breakpad symbols to <(_outputs)',
                  'process_outputs_as_sources': 1,
                },
              ],
              'dependencies': [
                'nw',
                '../breakpad/breakpad.gyp:dump_syms',
              ],
            }],
          ],
        }],
    }], # OS=="linux"
  ] # conditions
}


keep keep keep keep add keep keep keep keep


// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/api/base/base.h"

#include "base/logging.h"
#include "base/values.h"

namespace api {

Base::Base(int id,
           DispatcherHost* dispatcher_host,
           const base::DictionaryValue& option)
    : id_(id),
      dispatcher_host_(dispatcher_host) {
}

Base::~Base() {
}

void Base::Call(const std::string& method, const base::ListValue& arguments) {
  NOTREACHED() << "Uncatched call in Base"
               << " method:" << method
               << " arguments:" << arguments;
}

void Base::CallSync(const std::string& method,
                    const base::ListValue& arguments,
                    base::ListValue* result) {
  NOTREACHED() << "Uncatched callAsync in Base"
               << " method:" << method
               << " arguments:" << arguments;
}

}  // namespace api


// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/api/menu/menu.h"

#include "base/values.h"
#include "content/nw/src/api/dispatcher_host.h"
#include "content/nw/src/api/menuitem/menuitem.h"
#include "content/nw/src/nw_shell.h"

namespace api {

Menu::Menu(int id,
           DispatcherHost* dispatcher_host,
           const base::DictionaryValue& option)
    : Base(id, dispatcher_host, option) {
  Create(option);
}

Menu::~Menu() {
  Destroy();
}

void Menu::Call(const std::string& method,
                const base::ListValue& arguments) {
  if (method == "Append") {
    int object_id = 0;
    arguments.GetInteger(0, &object_id);
    Append(dispatcher_host()->GetApiObject<MenuItem>(object_id));
  } else if (method == "Insert") {
    int object_id = 0;
    arguments.GetInteger(0, &object_id);
    int pos = 0;
    arguments.GetInteger(1, &pos);
    Insert(dispatcher_host()->GetApiObject<MenuItem>(object_id), pos);
  } else if (method == "Remove") {
    int object_id = 0;
    arguments.GetInteger(0, &object_id);
    int pos = 0;
    arguments.GetInteger(1, &pos);
    Remove(dispatcher_host()->GetApiObject<MenuItem>(object_id), pos);
  } else if (method == "Popup") {
    int x = 0;
    arguments.GetInteger(0, &x);
    int y = 0;
    arguments.GetInteger(1, &y);
    Popup(x, y, content::Shell::FromRenderViewHost(
          dispatcher_host()->render_view_host()));
  } else {
    NOTREACHED() << "Invalid call to Menu method:" << method
                 << " arguments:" << arguments;
  }
}

}  // namespace api


// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/shell_content_browser_client.h"

#include "base/base_switches.h"
#include "base/command_line.h"
#include "base/files/file_path.h"
#include "base/file_util.h"
#include "base/strings/string_util.h"
#include "base/strings/string_number_conversions.h"
#include "base/threading/thread_restrictions.h"
#include "base/values.h"
#include "chrome/common/child_process_logging.h"
#include "content/browser/child_process_security_policy_impl.h"
#include "content/public/browser/browser_url_handler.h"
#include "content/nw/src/browser/printing/printing_message_filter.h"
#include "content/public/browser/render_process_host.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/resource_dispatcher_host.h"
#include "content/public/browser/web_contents.h"
#include "content/public/common/content_descriptors.h"
#include "content/public/common/content_switches.h"
#include "content/public/common/renderer_preferences.h"
#include "content/public/common/url_constants.h"
#include "content/nw/src/api/dispatcher_host.h"
#include "content/nw/src/breakpad_mac.h"
#include "content/nw/src/common/shell_switches.h"
#include "content/nw/src/browser/printing/print_job_manager.h"
#include "content/nw/src/browser/shell_devtools_delegate.h"
#include "content/nw/src/browser/shell_resource_dispatcher_host_delegate.h"
#include "content/nw/src/media/media_internals.h"
#include "content/nw/src/nw_package.h"
#include "content/nw/src/nw_shell.h"
#include "content/nw/src/nw_version.h"
#include "content/nw/src/shell_browser_context.h"
#include "content/nw/src/shell_browser_main_parts.h"
#include "geolocation/shell_access_token_store.h"
#include "url/gurl.h"
#include "ui/base/l10n/l10n_util.h"
#include "content/common/dom_storage/dom_storage_map.h"
#include "webkit/common/webpreferences.h"
#include "webkit/common/user_agent/user_agent_util.h"
#include "content/common/plugin_list.h"
#include "content/public/browser/plugin_service.h"

#if defined(OS_LINUX)
#include "base/linux_util.h"
#include "content/nw/src/crash_handler_host_linux.h"
#endif

using base::FileDescriptor;

namespace {

#if defined(OS_POSIX) && !defined(OS_MACOSX)
int GetCrashSignalFD(const CommandLine& command_line) {
  std::string process_type =
      command_line.GetSwitchValueASCII(switches::kProcessType);

  if (process_type == switches::kRendererProcess)
    return RendererCrashHandlerHostLinux::GetInstance()->GetDeathSignalSocket();

  if (process_type == switches::kPluginProcess)
    return PluginCrashHandlerHostLinux::GetInstance()->GetDeathSignalSocket();

  if (process_type == switches::kPpapiPluginProcess)
    return PpapiCrashHandlerHostLinux::GetInstance()->GetDeathSignalSocket();

  if (process_type == switches::kGpuProcess)
    return GpuCrashHandlerHostLinux::GetInstance()->GetDeathSignalSocket();

  return -1;
}
#endif  // defined(OS_POSIX) && !defined(OS_MACOSX)

}

namespace content {

ShellContentBrowserClient::ShellContentBrowserClient()
  : shell_browser_main_parts_(NULL),
    master_rph_(NULL) {
}

ShellContentBrowserClient::~ShellContentBrowserClient() {
}

BrowserMainParts* ShellContentBrowserClient::CreateBrowserMainParts(
    const MainFunctionParams& parameters) {
  shell_browser_main_parts_ = new ShellBrowserMainParts(parameters);
  return shell_browser_main_parts_;
}

WebContentsViewPort* ShellContentBrowserClient::OverrideCreateWebContentsView(
      WebContents* web_contents,
      RenderViewHostDelegateView** render_view_host_delegate_view) {
  std::string user_agent, rules;
  nw::Package* package = shell_browser_main_parts()->package();
  content::RendererPreferences* prefs = web_contents->GetMutableRendererPrefs();
  if (package->root()->GetString(switches::kmUserAgent, &user_agent)) {
    std::string name, version;
    package->root()->GetString(switches::kmName, &name);
    package->root()->GetString("version", &version);
    ReplaceSubstringsAfterOffset(&user_agent, 0, "%name", name);
    ReplaceSubstringsAfterOffset(&user_agent, 0, "%ver", version);
    ReplaceSubstringsAfterOffset(&user_agent, 0, "%nwver", NW_VERSION_STRING);
    ReplaceSubstringsAfterOffset(&user_agent, 0, "%webkit_ver", webkit_glue::GetWebKitVersion());
    ReplaceSubstringsAfterOffset(&user_agent, 0, "%osinfo", webkit_glue::BuildOSInfo());
    prefs->user_agent_override = user_agent;
  }
  if (package->root()->GetString(switches::kmRemotePages, &rules))
      prefs->nw_remote_page_rules = rules;

  prefs->nw_app_root_path = package->path();
  return NULL;
}

std::string ShellContentBrowserClient::GetApplicationLocale() {
  return l10n_util::GetApplicationLocale("en-US");
}

void ShellContentBrowserClient::AppendExtraCommandLineSwitches(
    CommandLine* command_line,
    int child_process_id) {
#if defined(OS_MACOSX)
  if (IsCrashReporterEnabled()) {
    command_line->AppendSwitchASCII(switches::kEnableCrashReporter,
                                    child_process_logging::GetClientId());
  }
#elif defined(OS_POSIX)
  if (IsCrashReporterEnabled()) {
    command_line->AppendSwitchASCII(switches::kEnableCrashReporter,
        child_process_logging::GetClientId() + "," + base::GetLinuxDistro());
  }

#endif  // OS_MACOSX
  if (command_line->GetSwitchValueASCII("type") != "renderer")
    return;
  if (child_process_id > 0) {
    content::RenderWidgetHost::List widgets =
      content::RenderWidgetHost::GetRenderWidgetHosts();
    for (size_t i = 0; i < widgets.size(); ++i) {
      if (widgets[i]->GetProcess()->GetID() != child_process_id)
        continue;
      if (!widgets[i]->IsRenderView())
        continue;

      const content::RenderWidgetHost* widget = widgets[i];
      DCHECK(widget);

      content::RenderViewHost* host = content::RenderViewHost::From(
        const_cast<content::RenderWidgetHost*>(widget));
      content::Shell* shell = content::Shell::FromRenderViewHost(host);
      if (shell) {
        if (!shell->nodejs())
          return;
        if (shell->is_devtools()) {
          // DevTools should have powerful permissions to load local
          // files by XHR (e.g. for source map)
          command_line->AppendSwitch(switches::kNodejs);
          return;
        }
      }
    }
  }
  nw::Package* package = shell_browser_main_parts()->package();
  if (package && package->GetUseNode()) {
    // Allow node.js
    command_line->AppendSwitch(switches::kNodejs);

    // Set cwd
    command_line->AppendSwitchPath(switches::kWorkingDirectory,
                                   package->path());

    // Check if we have 'node-main'.
    std::string node_main;
    if (package->root()->GetString(switches::kNodeMain, &node_main))
      command_line->AppendSwitchASCII(switches::kNodeMain, node_main);

    std::string snapshot_path;
    if (package->root()->GetString(switches::kSnapshot, &snapshot_path))
      command_line->AppendSwitchASCII(switches::kSnapshot, snapshot_path);

    int dom_storage_quota_mb;
    if (package->root()->GetInteger("dom_storage_quota", &dom_storage_quota_mb)) {
      content::DOMStorageMap::SetQuotaOverride(dom_storage_quota_mb * 1024 * 1024);
      command_line->AppendSwitchASCII(switches::kDomStorageQuota, base::IntToString(dom_storage_quota_mb));
    }
  }

  // without the switch, the destructor of the shell object will
  // shutdown renderwidgethost (RenderWidgetHostImpl::Shutdown) and
  // destory rph immediately. Then the channel error msg is caught by
  // SuicideOnChannelErrorFilter and the renderer is killed
  // immediately
#if defined(OS_POSIX)
  command_line->AppendSwitch(switches::kChildCleanExit);
#endif

}

void ShellContentBrowserClient::ResourceDispatcherHostCreated() {
  resource_dispatcher_host_delegate_.reset(
      new ShellResourceDispatcherHostDelegate());
  ResourceDispatcherHost::Get()->SetDelegate(
      resource_dispatcher_host_delegate_.get());
}

std::string ShellContentBrowserClient::GetDefaultDownloadName() {
  return "download";
}

MediaObserver* ShellContentBrowserClient::GetMediaObserver() {
  return MediaInternals::GetInstance();
}

void ShellContentBrowserClient::BrowserURLHandlerCreated(
    BrowserURLHandler* handler) {
}

ShellBrowserContext* ShellContentBrowserClient::browser_context() {
  return shell_browser_main_parts_->browser_context();
}

ShellBrowserContext*
    ShellContentBrowserClient::off_the_record_browser_context() {
  return shell_browser_main_parts_->off_the_record_browser_context();
}

AccessTokenStore* ShellContentBrowserClient::CreateAccessTokenStore() {
  return new ShellAccessTokenStore(browser_context());
}

void ShellContentBrowserClient::OverrideWebkitPrefs(
      RenderViewHost* render_view_host,
      const GURL& url,
      WebPreferences* prefs) {
  nw::Package* package = shell_browser_main_parts()->package();

  // Disable web security.
  prefs->dom_paste_enabled = true;
  prefs->javascript_can_access_clipboard = true;
  prefs->web_security_enabled = true;
  prefs->allow_file_access_from_file_urls = true;

  // Open experimental features.
  prefs->css_sticky_position_enabled = true;
  prefs->css_shaders_enabled = true;
  prefs->css_variables_enabled = true;

  // Disable plugins and cache by default.
  prefs->plugins_enabled = false;
  prefs->java_enabled = false;

  base::DictionaryValue* webkit;
  if (package->root()->GetDictionary(switches::kmWebkit, &webkit)) {
    webkit->GetBoolean(switches::kmJava, &prefs->java_enabled);
    webkit->GetBoolean(switches::kmPlugin, &prefs->plugins_enabled);
    FilePath plugins_dir = package->path();
    //PathService::Get(base::DIR_CURRENT, &plugins_dir);
    plugins_dir = plugins_dir.AppendASCII("plugins");

    PluginService* plugin_service = PluginService::GetInstance();
    plugin_service->AddExtraPluginDir(plugins_dir);
  }
}

bool ShellContentBrowserClient::ShouldTryToUseExistingProcessHost(
      BrowserContext* browser_context, const GURL& url) {
  ShellBrowserContext* shell_browser_context =
    static_cast<ShellBrowserContext*>(browser_context);
  if (shell_browser_context->pinning_renderer())
    return true;
  else
    return false;
}

bool ShellContentBrowserClient::IsSuitableHost(RenderProcessHost* process_host,
                                          const GURL& site_url) {
  return process_host == master_rph_;
}

net::URLRequestContextGetter* ShellContentBrowserClient::CreateRequestContext(
    BrowserContext* content_browser_context,
    ProtocolHandlerMap* protocol_handlers) {
  ShellBrowserContext* shell_browser_context =
      ShellBrowserContextForBrowserContext(content_browser_context);
  return shell_browser_context->CreateRequestContext(protocol_handlers);
}

net::URLRequestContextGetter*
ShellContentBrowserClient::CreateRequestContextForStoragePartition(
    BrowserContext* content_browser_context,
    const base::FilePath& partition_path,
    bool in_memory,
    ProtocolHandlerMap* protocol_handlers) {
  ShellBrowserContext* shell_browser_context =
      ShellBrowserContextForBrowserContext(content_browser_context);
  return shell_browser_context->CreateRequestContextForStoragePartition(
      partition_path, in_memory, protocol_handlers);
}

ShellBrowserContext*
ShellContentBrowserClient::ShellBrowserContextForBrowserContext(
    BrowserContext* content_browser_context) {
  if (content_browser_context == browser_context())
    return browser_context();
  DCHECK_EQ(content_browser_context, off_the_record_browser_context());
  return off_the_record_browser_context();
}

printing::PrintJobManager* ShellContentBrowserClient::print_job_manager() {
  return shell_browser_main_parts_->print_job_manager();
}

void ShellContentBrowserClient::RenderProcessHostCreated(
    RenderProcessHost* host) {
  int id = host->GetID();
  if (!master_rph_)
    master_rph_ = host;
  // Grant file: scheme to the whole process, since we impose
  // per-view access checks.
  content::ChildProcessSecurityPolicy::GetInstance()->GrantScheme(
      host->GetID(), chrome::kFileScheme);
  content::ChildProcessSecurityPolicy::GetInstance()->GrantScheme(
      host->GetID(), "app");

#if defined(ENABLE_PRINTING)
  host->GetChannel()->AddFilter(new PrintingMessageFilter(id));
#endif
}

bool ShellContentBrowserClient::IsHandledURL(const GURL& url) {
  if (!url.is_valid())
    return false;
  DCHECK_EQ(url.scheme(), StringToLowerASCII(url.scheme()));
  // Keep in sync with ProtocolHandlers added by
  // ShellURLRequestContextGetter::GetURLRequestContext().
  static const char* const kProtocolList[] = {
    chrome::kFileSystemScheme,
    chrome::kFileScheme,
    "app",
  };
  for (size_t i = 0; i < arraysize(kProtocolList); ++i) {
    if (url.scheme() == kProtocolList[i])
      return true;
  }
  return false;
}

void ShellContentBrowserClient::AllowCertificateError(
    int render_process_id,
    int render_view_id,
    int cert_error,
    const net::SSLInfo& ssl_info,
    const GURL& request_url,
    ResourceType::Type resource_type,
    bool overridable,
    bool strict_enforcement,
    const base::Callback<void(bool)>& callback,
    content::CertificateRequestResultType* result) {
  VLOG(1) << "AllowCertificateError: " << request_url;
  CommandLine* cmd_line = CommandLine::ForCurrentProcess();
  if (cmd_line->HasSwitch(switches::kIgnoreCertificateErrors)) {
    *result = content::CERTIFICATE_REQUEST_RESULT_TYPE_CONTINUE;
  }
  else
    *result = content::CERTIFICATE_REQUEST_RESULT_TYPE_DENY;
  return;
}

void ShellContentBrowserClient::GetAdditionalAllowedSchemesForFileSystem(
    std::vector<std::string>* additional_allowed_schemes) {
  ContentBrowserClient::GetAdditionalAllowedSchemesForFileSystem(
      additional_allowed_schemes);
  additional_allowed_schemes->push_back("app");
}

#if defined(OS_POSIX) && !defined(OS_MACOSX)
void ShellContentBrowserClient::GetAdditionalMappedFilesForChildProcess(
    const CommandLine& command_line,
    int child_process_id,
    std::vector<FileDescriptorInfo>* mappings) {
  int crash_signal_fd = GetCrashSignalFD(command_line);
  if (crash_signal_fd >= 0) {
    mappings->push_back(FileDescriptorInfo(kCrashDumpSignal,
                                           FileDescriptor(crash_signal_fd,
                                                          false)));
  }
}
#endif  // defined(OS_POSIX) && !defined(OS_MACOSX)

}  // namespace content


// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/browser/shell_toolbar_delegate_mac.h"

#include <string>

#import "base/mac/scoped_nsobject.h"
#include "base/strings/sys_string_conversions.h"
#include "content/nw/src/browser/native_window.h"
#include "content/nw/src/nw_shell.h"
#include "url/gurl.h"

static NSString *BackToolbarItemIdentifier = @"Back";
static NSString *ForwardToolbarItemIdentifier = @"Forward";
static NSString *RefreshToolbarItemIdentifier = @"Refresh";
static NSString *DevtoolsToolbarItemIdentifier = @"Devtools";
static NSString *EntryToolbarItemIdentifier = @"Entry";
static NSString *ReloadDevToolbarItemIdentifier = @"RefreshDev";

@implementation ShellToolbarDelegate

- (id)initWithShell:(content::Shell*)shell {
  if ((self = [super init])) {
    shell_ = shell;
  }
  return self;
}

- (void)buttonPressed:(id)sender {
  switch ([sender tag]) {
    case nw::NativeWindow::BUTTON_BACK:
      shell_->GoBackOrForward(-1);
      break;
    case nw::NativeWindow::BUTTON_FORWARD:
      shell_->GoBackOrForward(1);
      break;
    case nw::NativeWindow::BUTTON_REFRESH_OR_STOP:
      shell_->ReloadOrStop();
      break;
    case nw::NativeWindow::BUTTON_DEVTOOLS:
      shell_->ShowDevTools();
      break;
    case nw::NativeWindow::BUTTON_REFRESH_DEV:
      shell_->Reload(content::Shell::RELOAD_DEV);
      break;
  }
}

- (void)urlEntered:(id)sender {
  std::string url_string = base::SysNSStringToUTF8([sender stringValue]);
  if (!url_string.empty()) {
    GURL url(url_string);
    if (!url.has_scheme())
      url = GURL("http://" + url_string);
    shell_->LoadURL(url);
  }
}

- (void)setEnabled:(BOOL)enabled
         forButton:(nw::NativeWindow::TOOLBAR_BUTTON)button {
  switch (button) {
    case nw::NativeWindow::BUTTON_BACK:
      [back_button_ setEnabled:enabled];
      break;
    case nw::NativeWindow::BUTTON_FORWARD:
      [forward_button_ setEnabled:enabled];
      break;
    case nw::NativeWindow::BUTTON_REFRESH_OR_STOP:
      [refresh_stop_button_ setEnabled:enabled];
      break;
    case nw::NativeWindow::BUTTON_DEVTOOLS:
      [devtools_button_ setEnabled:enabled];
      break;
    case nw::NativeWindow::BUTTON_REFRESH_DEV:
      [refresh_dev_button_ setEnabled:enabled];
      break;
  }
}

- (void)setUrl:(NSString*)url {
  [entry_ setStringValue:url];
}

- (void)setIsLoading:(BOOL)loading {
  if (loading)
    [refresh_stop_button_
        setImage:[NSImage imageNamed:NSImageNameStopProgressTemplate]];
  else
    [refresh_stop_button_
        setImage:[NSImage imageNamed:NSImageNameRefreshTemplate]];
}

- (NSToolbarItem *)toolbar:(NSToolbar *)toolbar
     itemForItemIdentifier:(NSString *)identifier
 willBeInsertedIntoToolbar:(BOOL)flag {
  NSToolbarItem* item =
     [[NSToolbarItem alloc] initWithItemIdentifier:identifier];

  if ([identifier isEqualTo:EntryToolbarItemIdentifier]) {
    base::scoped_nsobject<NSTextField> entry(
        [[NSTextField alloc] initWithFrame:NSMakeRect(0, 0, 100, 24)]);
    entry_ = entry;
    [entry setAutoresizingMask:(NSViewWidthSizable | NSViewMinYMargin)];
    [entry setBezelStyle:NSTextFieldSquareBezel];
    [entry setTarget:self];
    [entry setAction:@selector(urlEntered:)];
    [[entry cell] setWraps:NO];
    [[entry cell] setScrollable:YES];
    [item setView:entry];
    [item setMinSize:NSMakeSize(100, 20)];
    [item setMaxSize:NSMakeSize(2000, 20)];
  } else {
    base::scoped_nsobject<NSButton> button([[NSButton alloc] init]);
    [button setBezelStyle:NSTexturedRoundedBezelStyle];
    [button setTarget:self];
    [button setAction:@selector(buttonPressed:)];
    item = [[NSToolbarItem alloc] initWithItemIdentifier:identifier];
    [item setView:button];
    [item setMinSize:NSMakeSize(28, 24)];
    [item setMaxSize:NSMakeSize(28, 24)];
    [item setToolTip:identifier];
  }

  if ([identifier isEqualTo:BackToolbarItemIdentifier]) {
    back_button_ = item;
    [item setImage:[NSImage imageNamed:NSImageNameGoLeftTemplate]];
    [item setTag:nw::NativeWindow::BUTTON_BACK];
  } else if ([identifier isEqualTo:ForwardToolbarItemIdentifier]) {
    forward_button_ = item;
    [item setImage:[NSImage imageNamed:NSImageNameGoRightTemplate]];
    [item setTag:nw::NativeWindow::BUTTON_FORWARD];
  } else if ([identifier isEqualTo:RefreshToolbarItemIdentifier]) {
    refresh_stop_button_ = item;
    [item setImage:[NSImage imageNamed:NSImageNameStopProgressTemplate]];
    [item setTag:nw::NativeWindow::BUTTON_REFRESH_OR_STOP];
  } else if ([identifier isEqualTo:DevtoolsToolbarItemIdentifier]) {
    devtools_button_ = item;
    [item setMinSize:NSMakeSize(28, 24)];
    [item setMaxSize:NSMakeSize(28, 24)];
    [item setImage:[NSImage imageNamed:NSImageNameActionTemplate]];
    [item setTag:nw::NativeWindow::BUTTON_DEVTOOLS];
  } else if ([identifier isEqualTo:ReloadDevToolbarItemIdentifier]) {
    refresh_dev_button_ = item;
    [item setImage:[NSImage imageNamed:NSImageNameRefreshTemplate]];
    [item setTag:nw::NativeWindow::BUTTON_REFRESH_DEV];
  }

  return [item autorelease];
}

- (NSArray *) toolbarAllowedItemIdentifiers: (NSToolbar *) toolbar {
  return [NSArray arrayWithObjects:BackToolbarItemIdentifier,
      ForwardToolbarItemIdentifier,
      RefreshToolbarItemIdentifier,
      EntryToolbarItemIdentifier,
      DevtoolsToolbarItemIdentifier,
      ReloadDevToolbarItemIdentifier,
      nil];
}

- (NSArray *) toolbarDefaultItemIdentifiers: (NSToolbar *)toolbar {
  return [NSArray arrayWithObjects:BackToolbarItemIdentifier,
      ForwardToolbarItemIdentifier,
      RefreshToolbarItemIdentifier,
      EntryToolbarItemIdentifier,
      DevtoolsToolbarItemIdentifier,
      ReloadDevToolbarItemIdentifier,
      nil];
}

@end


virtual QuotaPermissionContext* CreateQuotaPermissionContext() OVERRIDE;


// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

//{{NO_DEPENDENCIES}}
// Microsoft Visual C++ generated include file.
// Used by test_shell.rc
//

#define IDD_ALERT                 130
#define IDD_CONFIRM               131
#define IDD_PROMPT                132
#define IDD_LOGIN                 133
#define IDC_PROMPTEDIT            1005
#define IDC_DIALOGTEXT            1006
#define IDC_DIALOG_USERNAMETEXT   1007
#define IDC_DIALOG_PASSWORDTEXT   1008
#define IDC_DIALOG_MESSAGETEXT    1009
#define IDC_USERNAMEEDIT          1010
#define IDC_PASSWORDEDIT          1011

#ifndef IDC_STATIC
#define IDC_STATIC                -1
#endif
// Next default values for new objects
//
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS

#define _APS_NO_MFC               130
#define _APS_NEXT_RESOURCE_VALUE  129
#define _APS_NEXT_COMMAND_VALUE   32771
#define _APS_NEXT_CONTROL_VALUE   1000
#define _APS_NEXT_SYMED_VALUE     117
#endif
#endif


// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "content/nw/src/media/media_stream_devices_controller.h"

#include "base/values.h"
#include "content/nw/src/media/media_capture_devices_dispatcher.h"
#include "content/nw/src/media/media_internals.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/common/media_stream_request.h"

using content::BrowserThread;

namespace {

bool HasAnyAvailableDevice() {
  MediaCaptureDevicesDispatcher* dispatcher =
      MediaInternals::GetInstance()->GetMediaCaptureDevicesDispatcher();
  const content::MediaStreamDevices& audio_devices =
      dispatcher->GetAudioCaptureDevices();
  const content::MediaStreamDevices& video_devices =
      dispatcher->GetVideoCaptureDevices();

  return !audio_devices.empty() || !video_devices.empty();
};

const char kAudioKey[] = "audio";
const char kVideoKey[] = "video";

}  // namespace

MediaStreamDevicesController::MediaStreamDevicesController(
    const content::MediaStreamRequest& request,
    const content::MediaResponseCallback& callback)
    :
      request_(request),
      callback_(callback),
      has_audio_(content::IsAudioMediaType(request.audio_type) &&
                 !IsAudioDeviceBlockedByPolicy()),
      has_video_(content::IsVideoMediaType(request.video_type) &&
                 !IsVideoDeviceBlockedByPolicy()) {
}

MediaStreamDevicesController::~MediaStreamDevicesController() {}

#if 0
// static
void MediaStreamDevicesController::RegisterUserPrefs(
    PrefServiceSyncable* prefs) {
  prefs->RegisterBooleanPref(prefs::kVideoCaptureAllowed,
                             true,
                             PrefServiceSyncable::UNSYNCABLE_PREF);
  prefs->RegisterBooleanPref(prefs::kAudioCaptureAllowed,
                             true,
                             PrefServiceSyncable::UNSYNCABLE_PREF);
}
#endif

bool MediaStreamDevicesController::DismissInfoBarAndTakeActionOnSettings() {
  // If this is a no UI check for policies only go straight to accept - policy
  // check will be done automatically on the way.
  if (request_.request_type == content::MEDIA_OPEN_DEVICE) {
    Accept(false);
    return true;
  }

  if (request_.audio_type == content::MEDIA_TAB_AUDIO_CAPTURE ||
      request_.video_type == content::MEDIA_TAB_VIDEO_CAPTURE ||
      request_.video_type == content::MEDIA_DESKTOP_VIDEO_CAPTURE) {
    HandleTapMediaRequest();
    return true;
  }

#if 0
  // Deny the request if the security origin is empty, this happens with
  // file access without |--allow-file-access-from-files| flag.
  if (request_.security_origin.is_empty()) {
    Deny(false);
    return true;
  }
#endif
  // Deny the request if there is no device attached to the OS.
  if (!HasAnyAvailableDevice()) {
    Deny(false);
    return true;
  }

  // Check if any allow exception has been made for this request.
  if (IsRequestAllowedByDefault()) {
    Accept(false);
    return true;
  }
#if 0
  // Check if any block exception has been made for this request.
  if (IsRequestBlockedByDefault()) {
    Deny(false);
    return true;
  }

  // Check if the media default setting is set to block.
  if (IsDefaultMediaAccessBlocked()) {
    Deny(false);
    return true;
  }
#endif
  // Don't show the infobar.
  return true;
}

const std::string& MediaStreamDevicesController::GetSecurityOriginSpec() const {
  return request_.security_origin.spec();
}

void MediaStreamDevicesController::Accept(bool update_content_setting) {
  // Get the default devices for the request.
  content::MediaStreamDevices devices;
  media::GetDefaultDevicesForProfile(
                                     has_audio_,
                                     has_video_,
                                     &devices);

  callback_.Run(devices, scoped_ptr<content::MediaStreamUI>());
}

void MediaStreamDevicesController::Deny(bool update_content_setting) {
  callback_.Run(content::MediaStreamDevices(), scoped_ptr<content::MediaStreamUI>());
}

bool MediaStreamDevicesController::IsAudioDeviceBlockedByPolicy() const {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  return false;
}

bool MediaStreamDevicesController::IsVideoDeviceBlockedByPolicy() const {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  return false;
}

bool MediaStreamDevicesController::IsRequestAllowedByDefault() const {
  return true;
}

bool MediaStreamDevicesController::IsRequestBlockedByDefault() const {
  return false;
}

bool MediaStreamDevicesController::IsDefaultMediaAccessBlocked() const {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  return false;
}

void MediaStreamDevicesController::HandleTapMediaRequest() {
  content::MediaStreamDevices devices;

  if (request_.audio_type == content::MEDIA_TAB_AUDIO_CAPTURE) {
    devices.push_back(content::MediaStreamDevice(
          content::MEDIA_TAB_VIDEO_CAPTURE, "", ""));
  }
  if (request_.video_type == content::MEDIA_TAB_VIDEO_CAPTURE) {
    devices.push_back(content::MediaStreamDevice(
          content::MEDIA_TAB_AUDIO_CAPTURE, "", ""));
  }
  if (request_.video_type == content::MEDIA_DESKTOP_VIDEO_CAPTURE) {
    devices.push_back(content::MediaStreamDevice(
          content::MEDIA_DESKTOP_VIDEO_CAPTURE, std::string(), "Screen"));
  }

  callback_.Run(devices, scoped_ptr<content::MediaStreamUI>());
}

bool MediaStreamDevicesController::IsSchemeSecure() const {
  return (request_.security_origin.SchemeIsSecure());
}

bool MediaStreamDevicesController::ShouldAlwaysAllowOrigin() const {
  return true;
}


for (let i = 0; i < array.length; i++) {

// Base 64 encoding

const BASE_64_CHARS = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";

const BASE_64_VALS = Object.create(null);

const getChar = val => BASE_64_CHARS.charAt(val);
const getVal = ch => ch === '=' ? -1 : BASE_64_VALS[ch];

for (let i = 0; i < BASE_64_CHARS.length; i++) {
  BASE_64_VALS[getChar(i)] = i;
};

const encode = array => {
  if (typeof array === "string") {
    const str = array;
    array = newBinary(str.length);
    for (let i = 0; i < str.length; i++) {
      const ch = str.charCodeAt(i);
      if (ch > 0xFF) {
        throw new Error(
          "Not ascii. Base64.encode can only take ascii strings.");
      }

      array[i] = ch;
    }
  }

  const answer = [];
  let a = null;
  let b = null;
  let c = null;
  let d = null;

  array.forEach((elm, i) => {
    switch (i % 3) {
      case 0:
        a = (elm >> 2) & 0x3F;
        b = (elm & 0x03) << 4;
        break;
      case 1:
        b = b | (elm >> 4) & 0xF;
        c = (elm & 0xF) << 2;
        break;
      case 2:
        c = c | (elm >> 6) & 0x03;
        d = elm & 0x3F;
        answer.push(getChar(a));
        answer.push(getChar(b));
        answer.push(getChar(c));
        answer.push(getChar(d));
        a = null;
        b = null;
        c = null;
        d = null;
        break;
    }
  });

  if (a != null) {
    answer.push(getChar(a));
    answer.push(getChar(b));
    if (c == null) {
      answer.push('=');
    } else {
      answer.push(getChar(c));
    }

    if (d == null) {
      answer.push('=');
    }
  }

  return answer.join("");
};

// XXX This is a weird place for this to live, but it's used both by
// this package and 'ejson', and we can't put it in 'ejson' without
// introducing a circular dependency. It should probably be in its own
// package or as a helper in a package that both 'base64' and 'ejson'
// use.
const newBinary = len => {
  if (typeof Uint8Array === 'undefined' || typeof ArrayBuffer === 'undefined') {
    const ret = [];
    for (let i = 0; i < len; i++) {
      ret.push(0);
    }

    ret.$Uint8ArrayPolyfill = true;
    return ret;
  }
  return new Uint8Array(new ArrayBuffer(len));
};

const decode = str => {
  let len = Math.floor((str.length * 3) / 4);
  if (str.charAt(str.length - 1) == '=') {
    len--;
    if (str.charAt(str.length - 2) == '=') {
      len--;
    }
  }

  const arr = newBinary(len);

  let one = null;
  let two = null;
  let three = null;

  let j = 0;

  for (let i = 0; i < str.length; i++) {
    const c = str.charAt(i);
    const v = getVal(c);
    switch (i % 4) {
      case 0:
        if (v < 0) {
          throw new Error('invalid base64 string');
        }

        one = v << 2;
        break;
      case 1:
        if (v < 0) {
          throw new Error('invalid base64 string');
        }

        one = one | (v >> 4);
        arr[j++] = one;
        two = (v & 0x0F) << 4;
        break;
      case 2:
        if (v >= 0) {
          two = two | (v >> 2);
          arr[j++] = two;
          three = (v & 0x03) << 6;
        }

        break;
      case 3:
        if (v >= 0) {
          arr[j++] = three | v;
        }

        break;
    }
  }

  return arr;
};

export const Base64 = { encode, decode, newBinary };


.DS_Store
/.meteor
*~
/dev_bundle
/dev_bundle.xxx
/dev_bundle_XXX
/dev_bundle*.tar.gz
/android_bundle
/android_bundle*.tar.gz
/node_*.tar.gz
/mongo_*.tar.gz
/dist
\#*\#
.\#*
.idea
*.iml
*.sublime-project
*.sublime-workspace
/.vscode/
TAGS
*.log
*.out
npm-debug.log
universe
.babel-cache
mongo-test-output


var Future = Npm.require('fibers/future');

// A write fence collects a group of writes, and provides a callback
// when all of the writes are fully committed and propagated (all
// observers have been notified of the write and acknowledged it.)
//
DDPServer._WriteFence = function () {
  var self = this;

  self.armed = false;
  self.fired = false;
  self.retired = false;
  self.outstanding_writes = 0;
  self.before_fire_callbacks = [];
  self.completion_callbacks = [];
};

// The current write fence. When there is a current write fence, code
// that writes to databases should register their writes with it using
// beginWrite().
//
DDPServer._CurrentWriteFence = new Meteor.EnvironmentVariable;

_.extend(DDPServer._WriteFence.prototype, {
  // Start tracking a write, and return an object to represent it. The
  // object has a single method, committed(). This method should be
  // called when the write is fully committed and propagated. You can
  // continue to add writes to the WriteFence up until it is triggered
  // (calls its callbacks because all writes have committed.)
  beginWrite: function () {
    var self = this;

    if (self.retired)
      return { committed: function () {} };

    if (self.fired)
      throw new Error("fence has already activated -- too late to add writes");

    self.outstanding_writes++;
    var committed = false;
    return {
      committed: function () {
        if (committed)
          throw new Error("committed called twice on the same write");
        committed = true;
        self.outstanding_writes--;
        self._maybeFire();
      }
    };
  },

  // Arm the fence. Once the fence is armed, and there are no more
  // uncommitted writes, it will activate.
  arm: function () {
    var self = this;
    if (self === DDPServer._CurrentWriteFence.get())
      throw Error("Can't arm the current fence");
    self.armed = true;
    self._maybeFire();
  },

  // Register a function to be called once before firing the fence.
  // Callback function can add new writes to the fence, in which case
  // it won't fire until those writes are done as well.
  onBeforeFire: function (func) {
    var self = this;
    if (self.fired)
      throw new Error("fence has already activated -- too late to " +
                      "add a callback");
    self.before_fire_callbacks.push(func);
  },

  // Register a function to be called when the fence fires.
  onAllCommitted: function (func) {
    var self = this;
    if (self.fired)
      throw new Error("fence has already activated -- too late to " +
                      "add a callback");
    self.completion_callbacks.push(func);
  },

  // Convenience function. Arms the fence, then blocks until it fires.
  armAndWait: function () {
    var self = this;
    var future = new Future;
    self.onAllCommitted(function () {
      future['return']();
    });
    self.arm();
    future.wait();
  },

  _maybeFire: function () {
    var self = this;
    if (self.fired)
      throw new Error("write fence already activated?");
    if (self.armed && !self.outstanding_writes) {
      function invokeCallback (func) {
        try {
          func(self);
        } catch (err) {
          Meteor._debug("exception in write fence callback", err);
        }
      }

      self.outstanding_writes++;
      while (self.before_fire_callbacks.length > 0) {
        var callbacks = self.before_fire_callbacks;
        self.before_fire_callbacks = [];
        _.each(callbacks, invokeCallback);
      }
      self.outstanding_writes--;

      if (!self.outstanding_writes) {
        self.fired = true;
        var callbacks = self.completion_callbacks;
        self.completion_callbacks = [];
        _.each(callbacks, invokeCallback);
      }
    }
  },

  // Deactivate this fence so that adding more writes has no effect.
  // The fence must have already fired.
  retire: function () {
    var self = this;
    if (! self.fired)
      throw new Error("Can't retire a fence that hasn't fired.");
    self.retired = true;
  }
});


~name~

meteor test --once --driver-package meteortesting:mocha

TEST_WATCH=1 meteor test --full-app --driver-package meteortesting:mocha

meteor --production --extra-packages bundle-visualizer


switch (i % 3) {
case 0:
a = (elm >> 2) & 0x3F;
b = (elm & 0x03) << 4;
break;
case 1:


Plugin.registerSourceHandler("extension", function () {
  throw new Error("Error inside a source handler!");
});


// ## Token types

// The assignment of fine-grained, information-carrying type objects
// allows the tokenizer to store the information it has about a
// token in a way that is very cheap for the parser to look up.

// All token type variables start with an underscore, to make them
// easy to recognize.

// The `beforeExpr` property is used to disambiguate between regular
// expressions and divisions. It is set on all token types that can
// be followed by an expression (thus, a slash after them would be a
// regular expression).
//
// The `startsExpr` property is used to check if the token ends a
// `yield` expression. It is set on all token types that either can
// directly start an expression (like a quotation mark) or can
// continue an expression (like the body of a string).
//
// `isLoop` marks a keyword as starting a loop, which is important
// to know when parsing a label, in order to allow or disallow
// continue jumps to that label.

export class TokenType {
  constructor(label, conf = {}) {
    this.label = label
    this.keyword = conf.keyword
    this.beforeExpr = !!conf.beforeExpr
    this.startsExpr = !!conf.startsExpr
    this.isLoop = !!conf.isLoop
    this.isAssign = !!conf.isAssign
    this.prefix = !!conf.prefix
    this.postfix = !!conf.postfix
    this.binop = conf.binop || null
    this.updateContext = null
  }
}

function binop(name, prec) {
  return new TokenType(name, {beforeExpr: true, binop: prec})
}
const beforeExpr = {beforeExpr: true}, startsExpr = {startsExpr: true}

// Map keyword names to token types.

export const keywords = {}

// Succinct definitions of keyword token types
function kw(name, options = {}) {
  options.keyword = name
  return keywords[name] = new TokenType(name, options)
}

export const types = {
  num: new TokenType("num", startsExpr),
  regexp: new TokenType("regexp", startsExpr),
  string: new TokenType("string", startsExpr),
  name: new TokenType("name", startsExpr),
  eof: new TokenType("eof"),

  // Punctuation token types.
  bracketL: new TokenType("[", {beforeExpr: true, startsExpr: true}),
  bracketR: new TokenType("]"),
  braceL: new TokenType("{", {beforeExpr: true, startsExpr: true}),
  braceR: new TokenType("}"),
  parenL: new TokenType("(", {beforeExpr: true, startsExpr: true}),
  parenR: new TokenType(")"),
  comma: new TokenType(",", beforeExpr),
  semi: new TokenType(";", beforeExpr),
  colon: new TokenType(":", beforeExpr),
  dot: new TokenType("."),
  question: new TokenType("?", beforeExpr),
  arrow: new TokenType("=>", beforeExpr),
  template: new TokenType("template"),
  invalidTemplate: new TokenType("invalidTemplate"),
  ellipsis: new TokenType("...", beforeExpr),
  backQuote: new TokenType("`", startsExpr),
  dollarBraceL: new TokenType("${", {beforeExpr: true, startsExpr: true}),

  // Operators. These carry several kinds of properties to help the
  // parser use them properly (the presence of these properties is
  // what categorizes them as operators).
  //
  // `binop`, when present, specifies that this operator is a binary
  // operator, and will refer to its precedence.
  //
  // `prefix` and `postfix` mark the operator as a prefix or postfix
  // unary operator.
  //
  // `isAssign` marks all of `=`, `+=`, `-=` etcetera, which act as
  // binary operators with a very low precedence, that should result
  // in AssignmentExpression nodes.

  eq: new TokenType("=", {beforeExpr: true, isAssign: true}),
  assign: new TokenType("_=", {beforeExpr: true, isAssign: true}),
  incDec: new TokenType("++/--", {prefix: true, postfix: true, startsExpr: true}),
  prefix: new TokenType("!/~", {beforeExpr: true, prefix: true, startsExpr: true}),
  logicalOR: binop("||", 1),
  logicalAND: binop("&&", 2),
  bitwiseOR: binop("|", 3),
  bitwiseXOR: binop("^", 4),
  bitwiseAND: binop("&", 5),
  equality: binop("==/!=/===/!==", 6),
  relational: binop("</>/<=/>=", 7),
  bitShift: binop("<</>>/>>>", 8),
  plusMin: new TokenType("+/-", {beforeExpr: true, binop: 9, prefix: true, startsExpr: true}),
  modulo: binop("%", 10),
  star: binop("*", 10),
  slash: binop("/", 10),
  starstar: new TokenType("**", {beforeExpr: true}),

  // Keyword token types.
  _break: kw("break"),
  _case: kw("case", beforeExpr),
  _catch: kw("catch"),
  _continue: kw("continue"),
  _debugger: kw("debugger"),
  _default: kw("default", beforeExpr),
  _do: kw("do", {isLoop: true, beforeExpr: true}),
  _else: kw("else", beforeExpr),
  _finally: kw("finally"),
  _for: kw("for", {isLoop: true}),
  _function: kw("function", startsExpr),
  _if: kw("if"),
  _return: kw("return", beforeExpr),
  _switch: kw("switch"),
  _throw: kw("throw", beforeExpr),
  _try: kw("try"),
  _var: kw("var"),
  _const: kw("const"),
  _while: kw("while", {isLoop: true}),
  _with: kw("with"),
  _new: kw("new", {beforeExpr: true, startsExpr: true}),
  _this: kw("this", startsExpr),
  _super: kw("super", startsExpr),
  _class: kw("class", startsExpr),
  _extends: kw("extends", beforeExpr),
  _export: kw("export"),
  _import: kw("import"),
  _null: kw("null", startsExpr),
  _true: kw("true", startsExpr),
  _false: kw("false", startsExpr),
  _in: kw("in", {beforeExpr: true, binop: 7}),
  _instanceof: kw("instanceof", {beforeExpr: true, binop: 7}),
  _typeof: kw("typeof", {beforeExpr: true, prefix: true, startsExpr: true}),
  _void: kw("void", {beforeExpr: true, prefix: true, startsExpr: true}),
  _delete: kw("delete", {beforeExpr: true, prefix: true, startsExpr: true})
}


break;
case 1:
b = b | (elm >> 4) & 0xF;
c = (elm & 0xF) << 2;
break;
case 2:


====================================================================
For the license for Meteor itself, see LICENSE.txt in the root of
the repository.  This file contains the licenses for externally
maintained libraries.
====================================================================

----------
heapdump: https://github.com/bnoordhuis/node-heapdump
----------

Copyright (c) 2012, Ben Noordhuis <info@bnoordhuis.nl>

Permission to use, copy, modify, and/or distribute this software for any
purpose with or without fee is hereby granted, provided that the above
copyright notice and this permission notice appear in all copies.

THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.


keep keep replace replace keep keep keep keep keep


import assert from "assert";

// This verifies that babel-plugin-transform-strict-mode is enabled.
let expected;
try {
  console.log(arguments.callee.toString());
} catch (e) {
  expected = e;
}
assert.ok(expected instanceof TypeError);
assert.ok(/callee/.test(expected.message));

Plugin.registerCompiler({
  extensions: ["arson"]
}, () => new ArsonCompiler);

class ArsonCompiler {
  // This verifies that the babel-plugin-transform-class-properties plugin
  // enabled by package.json is respected.
  expectedName = "compile-arson";

  processFilesForTarget(inputFiles) {
    assert.strictEqual(this.expectedName, "compile-arson");
    assert.ok(inputFiles.length > 0);

    let vueCheckCount = 0;

    inputFiles.forEach(file => {
      const arson = file.require("arson");
      let encoded = file.getContentsAsString();
      const decoded = arson.decode(encoded);
      decoded.self = decoded;
      encoded = arson.encode(decoded);

      file.addJavaScript({
        path: file.getPathInPackage() + ".js",
        data: [
          'module.exportDefault(require("arson").decode(',
          "  " + JSON.stringify(encoded),
          "));",
          ""
        ].join("\n"),
        hash: file.getSourceHash()
      });

      if (file.getPackageName() === "modules-test-plugin") {
        const vueCompilerId = file.resolve("vue-template-compiler");
        // Make sure resolution does not use the "browser" field of
        // vue-template-compiler/package.json.
        assert.strictEqual(
          vueCompilerId.split("/").pop(),
          "index.js"
        );
        ++vueCheckCount;
      }
    });

    assert.ok(vueCheckCount > 0);
  }
}