Add files via upload

This commit is contained in:
Alexander David Frick 2022-07-09 18:44:13 -05:00 committed by GitHub
parent 316dc31ebd
commit af11b13150
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
78 changed files with 46842 additions and 0 deletions

View file

@ -0,0 +1,192 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright (c) 2022 Alex313031. -->
<grit-part>
<message name="IDS_APP_MANAGEMENT_CAMERA" desc="Label for the camera permission toggle.">
Camera
</message>
<message name="IDS_APP_MANAGEMENT_LOCATION" desc="Label for the location permission toggle." meaning="Geolocation">
Location
</message>
<message name="IDS_APP_MANAGEMENT_MICROPHONE" desc="Label for the microphone permission toggle.">
Microphone
</message>
<message name="IDS_APP_MANAGEMENT_NO_APPS_FOUND" desc="Text shown when a search of apps yeilds no results.">
No apps found
</message>
<message name="IDS_APP_MANAGEMENT_NOTIFICATIONS" desc="Label for notifications section in the app settings page.">
Notifications
</message>
<message name="IDS_APP_MANAGEMENT_PERMISSIONS" desc="Label for permissions section in the app settings page.">
Permissions
</message>
<message name="IDS_APP_MANAGEMENT_MORE_SETTINGS" desc="Label for a link to more settings and permissions for an app.">
More settings and permissions
</message>
<message name="IDS_APP_MANAGEMENT_PIN_TO_SHELF" desc="Label for the pin to shelf button in the app settings page.">
Pin to shelf
</message>
<message name="IDS_APP_MANAGEMENT_PRESET_WINDOW_SIZES" desc="Label for the preset window sizes toggle in the app settings page.">
Preset window sizes
</message>
<message name="IDS_APP_MANAGEMENT_WINDOW" desc="Label for changing window mode.">
Open as window
</message>
<message name="IDS_APP_MANAGEMENT_PRESET_WINDOW_SIZES_TEXT" desc="Label for the description of the window preset toggle in the app settings page.">
Use presets for phone, tablet, or resizable windows to prevent app from misbehaving
</message>
<message name="IDS_APP_MANAGEMENT_PRINTING" desc="Label for the printing permission toggle.">
Printers
</message>
<message name="IDS_APP_MANAGEMENT_SEARCH_PROMPT" desc="Prompt in search bar of main app management page.">
Search apps
</message>
<message name="IDS_APP_MANAGEMENT_UNINSTALL_APP" desc="Label for the uninstall button in the app settings page.">
Uninstall
</message>
<message name="IDS_APP_MANAGEMENT_CONTACTS" desc="Label for the Android contacts (address book) permission toggle.">
Contacts
</message>
<message name="IDS_APP_MANAGEMENT_STORAGE" desc="Label for the Android storage permission toggle.">
Storage
</message>
<message name="IDS_APP_MANAGEMENT_RUN_ON_OS_LOGIN" desc="Label for toggling running on OS Login mode.">
Start app when you sign in
</message>
<message name="IDS_APP_MANAGEMENT_POLICY_APP_POLICY_STRING" desc="Tooltip label explaining that an app cannot be uninstalled as it has been installed by an adminstrator.">
This app has been installed by your administrator.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_SETTINGS_TITLE" desc="Title for the intent sharing settings section.">
Opening <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph>supported links<ph name="END_LINK">&lt;/a&gt;</ph>
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_SHARING_APP_OPEN" desc="Label for the intent sharing option to open in a specified app.">
Open in <ph name="APP_NAME">$1<ex>Chrome browser</ex></ph>
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_SHARING_BROWSER_OPEN" desc="Label for the intent sharing option to open in the browser.">
Open in Thorium browser
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_SHARING_TAB_EXPLANATION" desc="Label for the intent sharing description for when the app is set to open in tab mode.">
<ph name="APP_NAME">$1<ex>Gmail</ex></ph> is set to open in a new browser tab, supported links will also open in the browser. <ph name="BEGIN_LINK_LEARN_MORE">&lt;a href="https://support.google.com/chromebook?p=app_intent" target="_blank"&gt;</ph>Learn more<ph name="END_LINK_LEARN_MORE">&lt;/a&gt;</ph>
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_SETTINGS_DIALOG_TITLE" desc="Title for the dialog which shows a list of supported links for a specified app.">
Supported links
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_CHANGE_BUTTON" desc="The text of a button that the user clicks to confrim a change in settings.">
Change
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TITLE" desc="The title of the dialog that asks the user for confirmation about overwritting preferred app settings.">
Change default app for supported links?
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TEXT_1_APP" desc="Text to explain to the user that an preferred app will be replaced, and the text states which app will be replaced.">
An app is set to open the same links as <ph name="APP_NAME">$1<ex>Gmail</ex></ph>. This will disable <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph> from opening supported links.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TEXT_2_APPS" desc="Text to explain to the user that 2 preferred apps will be replaced, and the text states which apps will be replaced.">
Other apps are set to open the same links as <ph name="APP_NAME">$1<ex>Gmail</ex></ph>. This will disable <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph> and <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph> from opening supported links.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TEXT_3_APPS" desc="Text to explain to the user that 3 preferred apps will be replaced, and the text states which apps will be replaced.">
Other apps are set to open the same links as <ph name="APP_NAME">$1<ex>Gmail</ex></ph>. This will disable <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>, <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph> and <ph name="APP_NAME_4">$4<ex>Photos</ex></ph> from opening supported links.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TEXT_4_APPS" desc="Text to explain to the user that 4 preferred apps will be replaced, and the text states the first 3 apps that will be replaced.">
Other apps are set to open the same links as <ph name="APP_NAME">$1<ex>Gmail</ex></ph>. This will disable <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>, <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph>, <ph name="APP_NAME_4">$4<ex>Photos</ex></ph> and 1 other app from opening supported links.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_DIALOG_TEXT_5_OR_MORE_APPS" desc="Text to explain to the user that 5 or more preferred apps will be replaced, and the text states the first 3 apps that will be replaced.">
Other apps are set to open the same links as <ph name="APP_NAME">$1<ex>Gmail</ex></ph>. This will disable <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>, <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph>, <ph name="APP_NAME_4">$4<ex>Photos</ex></ph> and <ph name="NUMBER_OF_OTHER_APPS">$5<ex>2</ex></ph> other apps from opening supported links.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_WARNING_TEXT_1_APP" desc="Text to explain to the user that an overlapping app will still open some supported links, and the text states which app will open links.">
Some supported links will still open in <ph name="APP_NAME">$1<ex>Gmail</ex></ph>.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_WARNING_TEXT_2_APPS" desc="Text to explain to the user that 2 overlapping apps will still open some supported links, and the text states which apps will open links.">
Some supported links will still open in <ph name="APP_NAME">$1<ex>Gmail</ex></ph> or <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_WARNING_TEXT_3_APPS" desc="Text to explain to the user that 3 overlapping apps will still open some supported links, and the text states which apps will open links.">
Some supported links will still open in <ph name="APP_NAME">$1<ex>Gmail</ex></ph>, <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph> or <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph>.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_WARNING_TEXT_4_APPS" desc="Text to explain to the user that 4 overlapping apps will still open some supported links, and the text states the first 3 apps that will open links.">
Some supported links will still open in <ph name="APP_NAME">$1<ex>Gmail</ex></ph>, <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>, <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph> and 1 other app.
</message>
<message name="IDS_APP_MANAGEMENT_INTENT_OVERLAP_WARNING_TEXT_5_OR_MORE_APPS" desc="Text to explain to the user that 5 or more overlapping apps will still open some supported links, and the text states the first 3 apps that will open links.">
Some supported links will still open in <ph name="APP_NAME">$1<ex>Gmail</ex></ph>, <ph name="APP_NAME_2">$2<ex>EmailReader</ex></ph>, <ph name="APP_NAME_3">$3<ex>PDFViewer</ex></ph> and <ph name="NUMBER_OF_OTHER_APPS">$4<ex>2</ex></ph> other apps.
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TITLE" desc="Title for App Details Section">
App details
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_ANDROID" desc="Text for Android app type">
Android App
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_CHROME" desc="Text for Chrome app type">
Thorium App
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_WEB" desc="Text for Web app type">
Web App
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_SYSTEM" desc="Text for System app type">
System App
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_CROS_SYSTEM" desc="Text for ChromeOS System app type">
ThoriumOS System App
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_INSTALL_SOURCE_WEB_STORE" desc="Text for Chrome Web Store installation source">
Thorium Web Store
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_INSTALL_SOURCE_PLAY_STORE" desc="Text for Google Play Store installation source">
Google Play Store
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_INSTALL_SOURCE_BROWSER" desc="Text for Chrome browser installation source for Web App">
Web App installed from Thorium browser
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_TYPE_AND_SOURCE_COMBINED" desc="Full text for installation source and app type line">
<ph name="APP_TYPE">$1<ex>Web App</ex></ph> installed from <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph><ph name="INSTALL_SOURCE">$2<ex>Google Play Store</ex></ph><ph name="END_LINK">&lt;/a&gt;</ph>
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_VERSION" desc="Text for application version">
Version: <ph name="APP_VERSION">$1<ex>17.2</ex></ph>
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_STORAGE_TITLE" desc="Text for title of storage section for storage related to the app and its associated files">
Storage
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_APP_SIZE" desc="Text for app size label for the amount of storage the app itself is using">
App size: <ph name="APP_SIZE">$1<ex>100 MB</ex></ph>
</message>
<message name="IDS_APP_MANAGEMENT_APP_DETAILS_DATA_SIZE" desc="Text for data size label for the amount of storage the app's associated files is using">
Data stored in app: <ph name="APP_SIZE">$1<ex>100 MB</ex></ph>
</message>
<!-- File Handling -->
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_HEADER" desc="Main text for toggling a web app's ability to use the File Handling API. This controls whether the app can appear in an 'Open With' list in a file's context menu.">
Include this app as an option when opening files
</message>
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_OVERFLOW_DIALOG_TITLE" desc="Title for a dialog that shows all the supported file types (file extensions) that are handled by an app. Only shown when there are 5 or more file types.">
Supported file types
</message>
<if expr="is_win">
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_SET_DEFAULTS_LINK" desc="Further explanation of the File Handling API, including text describing the purpose of the toggle (referencing the Windows File Explorer) and a link to change Windows' default filetype associations.">
You can open and edit supported files with this app from the File Explorer or other apps. To control which files open in this app by default, go to <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph>Windows settings<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
</if>
<if expr="chromeos_ash or chromeos_lacros">
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_SET_DEFAULTS_LINK" desc="Further explanation of the File Handling API, including text describing the purpose of the toggle (referencing the ChromeOS Files app) and a link to a learn more link for default filetype associations.">
You can open and edit supported files with this app from the Files app or other apps. To control which files open this app by default, <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph>learn how to set default apps on your device<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
</if>
<if expr="is_macosx">
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_SET_DEFAULTS_LINK" desc="Further explanation of the File Handling API, including text describing the purpose of the toggle (referencing the Mac OS Finder app) and a link to a learn more link for default filetype associations.">
You can open and edit supported files with this app from Finder or other apps. To control which files open this app by default, <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph>learn how to set default apps on your device<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
</if>
<if expr="is_fuchsia or is_linux">
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_SET_DEFAULTS_LINK" desc="Further explanation of the File Handling API, including text describing the purpose of the toggle (referencing a generic Linux file browser app) and a link to a learn more link for default filetype associations.">
You can open and edit supported files with this app from your file browser or other apps. To control which files open this app by default, <ph name="BEGIN_LINK">&lt;a href="#"&gt;</ph>learn how to set default apps on your device<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
</if>
<message name="IDS_APP_MANAGEMENT_FILE_HANDLING_TYPES" desc="A label describing the file types (extensions) that an app has advertised the ability to open. If there are 1-4 file types, all will be shown. If there are more than 4, the extras will be truncated and a link will be added which, when clicked, shows the elided extensions. [ICU_Syntax]">
{FILE_TYPE_COUNT, plural,
=1 {Supported file type: <ph name="FILE_TYPE1">{FILE_TYPE1}<ex>TXT</ex></ph>}
=2 {Supported file types: <ph name="FILE_TYPE1">{FILE_TYPE1}<ex>TXT</ex></ph>, <ph name="FILE_TYPE2">{FILE_TYPE2}<ex>CSV</ex></ph>}
=3 {Supported file types: <ph name="FILE_TYPE1">{FILE_TYPE1}<ex>TXT</ex></ph>, <ph name="FILE_TYPE2">{FILE_TYPE2}<ex>CSV</ex></ph>, <ph name="FILE_TYPE3">{FILE_TYPE3}<ex>DOC</ex></ph>}
=4 {Supported file types: <ph name="FILE_TYPE1">{FILE_TYPE1}<ex>TXT</ex></ph>, <ph name="FILE_TYPE2">{FILE_TYPE2}<ex>CSV</ex></ph>, <ph name="FILE_TYPE3">{FILE_TYPE3}<ex>DOC</ex></ph>, <ph name="FILE_TYPE4">{FILE_TYPE4}<ex>DOCX</ex></ph>}
other {Supported file types: <ph name="FILE_TYPE1">{FILE_TYPE1}<ex>TXT</ex></ph>, <ph name="FILE_TYPE2">{FILE_TYPE2}<ex>CSV</ex></ph>, <ph name="FILE_TYPE3">{FILE_TYPE3}<ex>DOC</ex></ph>, <ph name="FILE_TYPE4">{FILE_TYPE4}<ex>DOCX</ex></ph> (<ph name="LINK">&lt;a href="{LINK}"&gt;</ph>and {OVERFLOW_COUNT} more<ph name="END_LINK">&lt;/a&gt;</ph>)}
}
</message>
</grit-part>

View file

@ -0,0 +1,2 @@
INTERNAL_NAME=thorium_exe
ORIGINAL_FILENAME=thorium.exe

View file

@ -0,0 +1,22 @@
<?xml version="1.0" encoding="Windows-1252"?>
<VisualStudioPropertySheet
ProjectType="Visual C++"
Version="8.00"
Name="chrome_exe"
InheritedPropertySheets="$(SolutionDir)..\third_party\breakpad\using_breakpad.vsprops"
>
<Tool
Name="VCCLCompilerTool"
PreprocessorDefinitions="_CRT_SECURE_NO_DEPRECATE"
/>
<Tool
Name="VCLinkerTool"
DelayLoadDLLs="ole32.dll;oleaut32.dll"
OutputFile="$(OutDir)\thorium.exe"
ProgramDatabaseFile="$(OutDir)\$(ProjectName).pdb"
/>
<Tool
Name="VCResourceCompilerTool"
AdditionalIncludeDirectories="$(IntDir)"
/>
</VisualStudioPropertySheet>

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,165 @@
.\" This file is processed to generate manpages in the
.\" build diretory.
.TH @@PACKAGE@@ 1 "" "" "USER COMMANDS"
.SH NAME
@@PACKAGE@@ \- the web browser from Alex313031
.SH SYNOPSIS
.B @@PACKAGE@@
[\fIOPTION\fR] [\fIPATH\fR|\fIURL\fR]
.SH DESCRIPTION
See the Thorium Repository for help on using the browser.
.IP
<https://github.com/Alex313031/Thorium/>
.PP
This manpage only describes invocation, environment, and arguments.
.SH OPTIONS
@@MENUNAME@@ has hundreds of undocumented command-line flags that are added
and removed at the whim of the developers. Here, we document relatively
stable flags.
.TP
\fB\-\-user\-data\-dir\fR=\fIDIR\fR
Specifies the directory that user data (your "profile") is kept in.
Defaults to
.I $HOME/.config/@@PACKAGE@@ .
Separate instances of @@MENUNAME@@ must use separate user data directories;
repeated invocations of @@PACKAGE@@ will reuse an existing process for
a given user data directory.
.TP
\fB\-\-incognito\fR
Open in incognito mode.
.TP
\fB\-\-new-window\fR
If \fIPATH\fR or \fIURL\fR is given, open it in a new window.
.TP
\fB\-\-proxy-server\fR=\fIhost:port\fR
Specify the HTTP/SOCKS4/SOCKS5 proxy server to use for requests. This
overrides any environment variables or settings picked via the options dialog.
An individual proxy server is specified using the format:
[<proxy-scheme>://]<proxy-host>[:<proxy-port>]
Where <proxy-scheme> is the protocol of the proxy server, and is one of:
"http", "socks", "socks4", "socks5".
If the <proxy-scheme> is omitted, it defaults to "http". Also note that
"socks" is equivalent to "socks5".
Examples:
--proxy-server="foopy:99"
Use the HTTP proxy "foopy:99" to load all URLs.
--proxy-server="socks://foobar:1080"
Use the SOCKS v5 proxy "foobar:1080" to load all URLs.
--proxy-server="socks4://foobar:1080"
Use the SOCKS v4 proxy "foobar:1080" to load all URLs.
--proxy-server="socks5://foobar:66"
Use the SOCKS v5 proxy "foobar:66" to load all URLs.
It is also possible to specify a separate proxy server for different URL types,
by prefixing the proxy server specifier with a URL specifier:
Example:
--proxy-server="https=proxy1:80;http=socks4://baz:1080"
Load https://* URLs using the HTTP proxy "proxy1:80". And load http://*
URLs using the SOCKS v4 proxy "baz:1080".
.TP
\fB\-\-no-proxy-server\fR
Disables the proxy server. Overrides any environment variables or
settings picked via the options dialog.
.TP
\fB\-\-proxy-auto-detect\fR
Autodetect proxy configuration. Overrides any environment variables
or settings picked via the options dialog.
.TP
\fB\-\-proxy-pac-url\fR=\fIURL\fR
Specify proxy autoconfiguration URL. Overrides any environment variables
or settings picked via the options dialog.
.TP
\fB\-\-password-store\fR=<\fIbasic\fR|\fIgnome\fR|\fIkwallet\fR>
Set the password store to use. The default is to automatically detect based
on the desktop environment. \fIbasic\fR selects the built in, unencrypted
password store. \fIgnome\fR selects Gnome keyring. \fIkwallet\fR selects
(KDE) KWallet. (Note that KWallet may not work reliably outside KDE.)
.TP
\fB\-\-version\fR
Show version information.
.PP
As a GTK+ app, @@MENUNAME@@ also obeys GTK+ command-line flags, such
as
.BR \-\-display .
See the GTK documentation for more:
.IP
<http://library.gnome.org/devel/gtk/stable/gtk-running.html>
.IP
<http://library.gnome.org/devel/gtk/stable/gtk-x11.html>
.SH ENVIRONMENT
@@MENUNAME@@ obeys the following environment variables:
.TP
.B all_proxy
Shorthand for specifying all of
.B http_proxy, https_proxy, ftp_proxy
.TP
.B http_proxy, https_proxy, ftp_proxy
The proxy servers used for HTTP, HTTPS, and FTP.
.I Note:
because Gnome/KDE proxy settings may propagate into these variables
in some terminals, this variable is ignored (in preference for actual
system proxy settings) when running under Gnome or KDE. Use the
command-line flags to set these when you want to force their values.
.TP
.B auto_proxy
Specify proxy autoconfiguration. Defined and empty autodetects; otherwise,
it should be an autoconfig URL. But see above note about Gnome/KDE.
.TP
.B SOCKS_SERVER
SOCKS proxy server (defaults to SOCKS v4, also set
.B SOCKS_VERSION=5
to use SOCKS v5).
.TP
.B no_proxy
Comma separated list of hosts or patterns to bypass proxying.
.SH FILES
.TP
.I $HOME/.config/@@PACKAGE@@
Default directory for configuration data.
.TP
.I $HOME/.cache/@@PACKAGE@@
Default directory for cache data. (Why? See
<http://standards.freedesktop.org/basedir-spec/latest/> .)
.SH BUGS
Bug tracker:
.IP
http://code.google.com/p/chromium/issues/list & https://github.com/Alex313031/Thorium/issues
.PP
Be sure to do your search within "All Issues" before reporting bugs,
and be sure to pick the "Defect on Linux" template when filing a new one.
.SH AUTHOR
The Chromium team and Alex313031 \- <http://www.chromium.org>

View file

@ -0,0 +1,310 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Copyright (c) 2022 Alex313031. -->
<!-- Settings-specific Chromium strings (included from chromium_strings.grd). -->
<grit-part>
<!-- Shared across multiple page -->
<if expr="not chromeos_ash">
<message name="IDS_RELAUNCH_CONFIRMATION_DIALOG_TITLE" desc="The title of the modal dialog that we show when users click on relaunch and they have open Incognito windows. The dialog serves to warn the users about losing their Incognito windows if they proceed with the relaunch.">
Relaunch Thorium?
</message>
</if>
<!-- About Page -->
<message name="IDS_SETTINGS_ABOUT_PROGRAM" desc="Menu title for the About Chromium page.">
About Thorium
</message>
<message name="IDS_SETTINGS_GET_HELP_USING_CHROME" desc="Text of the button which takes the user to the Chrome help page.">
Get help with Thorium
</message>
<if expr="not chromeos_ash">
<message name="IDS_SETTINGS_UPGRADE_UPDATING" desc="Status label: Updating Chromium">
Updating Thorium
</message>
<message name="IDS_SETTINGS_UPGRADE_UPDATING_PERCENT" desc="Status label: Updating Chromium (90%)">
Updating Thorium (<ph name="PROGRESS_PERCENT">$1<ex>90%</ex></ph>)
</message>
<message name="IDS_SETTINGS_UPGRADE_SUCCESSFUL_RELAUNCH" desc="Status label: Successfully updated Chromium">
Nearly up to date! Relaunch Thorium to finish updating.
</message>
<message name="IDS_SETTINGS_UPGRADE_UP_TO_DATE" desc="Status label: Already up to date (Chromium)">
Thorium is up to date
</message>
</if>
<if expr="chromeos_ash">
<message name="IDS_SETTINGS_ABOUT_OS" desc="Menu title for the About ChromiumOS page.">
About ThoriumOS
</message>
<message name="IDS_OS_SETTINGS_TAG_OS_VERSION" desc="Text for search result item which, when clicked, navigates the user to about ChromeOS settings, which gives information about the current ChromeOS version.">
ThoriumOS version
</message>
<message name="IDS_SETTINGS_ABOUT_SEE_OS_SETTINGS_FOR_UPDATE_MESSAGE" desc="Message shown to users on Chromium browser settings which alerts the user that OS updates are shown in ChromiumOS settings.">
To see if your device is up to date, go to <ph name="LINK_BEGIN">&lt;a href="chrome://os-settings/help"&gt;</ph>ThoriumOS Settings<ph name="LINK_END">&lt;/a&gt;</ph>
</message>
<message name="IDS_SETTINGS_GET_HELP_USING_CHROME_OS" desc="Text of the button which takes the user to the Chrome help page.">
Get help with ThoriumOS
</message>
</if>
<!-- Autofill Page -->
<message name="IDS_SETTINGS_GOOGLE_PAYMENTS_CACHED" desc="Label that will be used to show that a credit card comes from Google Pay and is saved locally. This should follow the casing of the 'Google Pay' and 'Chrome' brands. 'Copied to Chromium' is short for 'The credit card is copied to Chromium'. 'Google Pay' should not be translated as it is the product name.">
Google Pay (copied to Thorium)
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_OFFLINE" desc="Error message when the password check can't be completed because the user is offline.">
Thorium can't check your passwords. Try checking your internet connection.
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_SIGNED_OUT" desc="Error message when the password check can't be completed because the user is not signed in.">
Thorium can check your passwords when you sign in with your Google Account
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_NO_PASSWORDS" desc="Error message when the password check can't be completed since no passwords could be checked.">
No saved passwords. Thorium can check your passwords when you save them.
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_QUOTA_LIMIT_GOOGLE_ACCOUNT" desc="Error message when the password check can't be completed since the user hit the quota limit, but the user is able to check their passwords in their Google account.">
Thorium can't check your passwords. Try again after 24 hours or <ph name="BEGIN_LINK">&lt;a href="$1" target="_blank"&gt;</ph>check passwords in your Google Account<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_QUOTA_LIMIT" desc="Error message when the password check can't be completed since the user hit the quota limit.">
Thorium can't check your passwords. Try again after 24 hours.
</message>
<message name="IDS_SETTINGS_CHECK_PASSWORDS_ERROR_GENERIC" desc="Error message when the password check can't be completed for an unspecified reason.">
Thorium can't check your passwords. Try again later.
</message>
<message name="IDS_SETTINGS_NO_COMPROMISED_CREDENTIALS_LABEL" desc="Label which is shown when there were no compromised passwords detected.">
Thorium will notify you when you sign in with a compromised password
</message>
<message name="IDS_SETTINGS_SIGNED_OUT_USER_LABEL" desc="Label which is shown at the top of the compromised password section if user is signed out.">
To check if your passwords are safe from data breaches and other security issues, <ph name="BEGIN_LINK">&lt;a target='_blank' href='$1'&gt;</ph>sign in to Thorium<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
<message name="IDS_SETTINGS_SIGNED_OUT_USER_HAS_COMPROMISED_CREDENTIALS_LABEL" desc="Label which is shown at the bottom of the compromised password section if user is signed out and has compromised credentials.">
To check if your other passwords are safe from data breaches and other security issues, <ph name="BEGIN_LINK">&lt;a target='_blank' href='$1'&gt;</ph>sign in to Thorium<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
<message name="IDS_SETTINGS_WEAK_PASSWORDS_DESCRIPTION_GENERATION" desc="Information about why weak passwords are a security issue and what syncing user should do to fix the problem. Has a link.">
Weak passwords are easy to guess. Let Thorium <ph name="BEGIN_LINK">&lt;a target='_blank' href='$1'&gt;</ph>create and remember strong passwords for you<ph name="END_LINK">&lt;/a&gt;</ph>.
</message>
<message name="IDS_SETTINGS_COMPROMISED_EDIT_DISCLAIMER_DESCRIPTION" desc="A description for the dialog which tells the user to edit password in Chromium if it was changed already.">
If so, please edit your saved password in Thorium so it matches your new password.
</message>
<!-- Default Browser Page -->
<if expr="not chromeos_ash">
<message name="IDS_SETTINGS_DEFAULT_BROWSER_DEFAULT" desc="The text displayed when Chrome is the default browser">
Thorium is your default browser
</message>
<message name="IDS_SETTINGS_DEFAULT_BROWSER_MAKE_DEFAULT" desc="Default browser checkbox label">
Make Thorium the default browser
</message>
<message name="IDS_SETTINGS_DEFAULT_BROWSER_ERROR" desc="The text displayed when Chrome cannot determine or set the default browser">
Thorium cannot determine or set the default browser
</message>
<message name="IDS_SETTINGS_DEFAULT_BROWSER_SECONDARY" desc="The text displayed when Chromium is installed in side-by-side mode, which does not support setting as the default browser.">
This is a secondary installation of Thorium, and cannot be made your default browser.
</message>
</if>
<!-- Main Page -->
<if expr="chromeos_ash or chromeos_lacros">
<!-- No target="_blank" because OS settings opens its own window. -->
<message name="IDS_SETTINGS_OS_SETTINGS_BANNER" desc="Banner displayed in browser settings page that links to OS settings.">
If a setting doesn't show on this page, look in your <ph name="LINK_BEGIN">&lt;a href="$1<ex>https://google.com/</ex>"&gt;</ph>
ThoriumOS settings<ph name="LINK_END">&lt;/a&gt;</ph>
</message>
</if>
<!-- Privacy Page -->
<message name="IDS_SETTINGS_SPELLING_PREF_DESC" desc="Description of using a web serviced to help resolve spelling errors. It is important to convey that what the user types will be sent to Google.">
To fix spelling errors, Thorium sends the text you type in text fields to Google
</message>
<message name="IDS_SETTINGS_RESTART_TO_APPLY_CHANGES" desc="Description in the snackbar to restart Chrome and apply changes.">
To apply your changes, relaunch Thorium
</message>
<if expr="not chromeos_ash and not chromeos_lacros">
<message name="IDS_SETTINGS_SIGNIN_ALLOWED" desc="The title of the preference to allow to sign-in to Chrome">
Allow Thorium sign-in
</message>
<message name="IDS_SETTINGS_SIGNIN_ALLOWED_DESC" desc="The description of the preference to allow to sign-in to Chrome">
By turning this off, you can sign in to Google sites like Gmail without signing in to Thorium
</message>
</if>
<!-- Site Settings -->
<message name="IDS_SETTINGS_SITE_SETTINGS_PDFS_BLOCKED" desc="Label for the disabled option of the pdfs content setting.">
Open PDFs in Thorium
</message>
<if expr="not chromeos_ash and not chromeos_lacros">
<message name="IDS_SETTINGS_COOKIES_CLEAR_ON_EXIT_DESC" desc="Secondary text for the toggle that allows the user to automatically delete their cookies and site data when they close all browser windows. This sublabel clarifies that when the toggle is enabled the user will be signed out of Chrome each time they close all Chrome windows.">
When on, you'll also be signed out of Thorium
</message>
</if>
<!-- Privacy Guide -->
<message name="IDS_SETTINGS_PRIVACY_GUIDE_PROMO_BODY" desc="Body text of a card in the settings page that explains what the 'Privacy Guide' feature is.">
Review key privacy and security controls in Thorium
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_CLEAR_ON_EXIT_FEATURE_DESCRIPTION1" desc="A part of the feature description of 'clear cookies on exit' card in the 'Privacy Guide'.">
When you close all Thorium windows, cookies and site data are automatically cleared
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_CLEAR_ON_EXIT_FEATURE_DESCRIPTION2" desc="A part of the feature description of 'clear cookies on exit' card in the 'Privacy Guide'.">
You will be <ph name="BEGIN_BOLD">&lt;b&gt;</ph>signed out of most sites<ph name="END_BOLD">&lt;/b&gt;</ph> when you close Thorium. If sync is off, you will also be <ph name="BEGIN_BOLD">&lt;b&gt;</ph>signed out of Google services and Thorium<ph name="END_BOLD">&lt;/b&gt;</ph>.
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_CLEAR_ON_EXIT_FEATURE_DESCRIPTION3" desc="A part of the feature description of 'clear cookies on exit' card in the 'Privacy Guide'.">
Sites you visit remember your information until you close Thorium
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_SAFE_BROWSING_CARD_STANDARD_PROTECTION_FEATURE_DESCRIPTION2" desc="A part of the feature description of the standard protection section of the safe browsing card in the 'Privacy Guide'.">
Checks URLs with a list of unsafe sites stored in Thorium
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_SAFE_BROWSING_CARD_STANDARD_PROTECTION_PRIVACY_DESCRIPTION1" desc="A part of the privacy description of the standard protection section of the safe browsing card in the 'Privacy Guide'.">
If a site tries to steal your password, or when you download a harmful file, Thorium may also send URLs, including bits of page content, to Safe Browsing
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_COMPLETION_CARD_PRIVACY_SANDBOX_SUB_LABEL" desc="Text of the Privacy Sandbox sublabel in the completion card of the 'Privacy Guide'.">
Thorium is exploring new features that allow sites to deliver the same browsing experience using less of your data
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_COMPLETION_CARD_WAA_SUB_LABEL" desc="Text of the Web and App Activity sublabel in the completion card of the 'Privacy Guide'.">
Choose whether to include Thorium history for more personalized experiences in Google services
</message>
<message name="IDS_SETTINGS_PRIVACY_GUIDE_MSBB_PRIVACY_DESCRIPTION2" desc="A part of the privacy description of 'make searches and browsing better' in the 'Privacy Guide'.">
If you also share Thorium usage reports, those reports include the URLs you visit
</message>
<!-- Privacy Sandbox -->
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_TOPICS_TITLE" desc="TOPICS API A sub title that describes the first of 2 ways a site can get info from Chrome in order to target ads to the user. Topics of interest include things like “Live comedy” and “Rock music”. Chrome estimates these interests based on the sites users visit. * “Your”: we need to convey a sense of ownership, even if the user didnt explicitly choose the interests were talking about. Without the “your”, it could sound like Chrome is simply building a generic library of interests. * “estimated”: Its an “estimation”, and we dont want to suggest that we know with certainty the users interests. Avoid words like “guess”, “establish”, “define”, etc. (in place of “estimate”). * “by Chrome”: This is new behavior for a browser (Chrome) to take an active role in processing user data for the purposes of showing ads. Its important to convey “chrome”, the actor in this case.">
Your interests as estimated by Thorium
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_TOPICS_DATA_TYPES" desc="TOPICS API Bullet 1 of 3 that appear beneath the “Your interests as estimated by Chrome” subtitle. We break the description into the 3 pieces users most care about: 1) what data, 2) why this data, 3) what can I do about it? * “What data is used:” is bold and serves as a label to help people skimming the page. * “Your browsing history”: The users browsing history is available beneath the “History” menu at Chromes top level. The Topics API estimates topics of interest based on sites in the users browsing history that are participating in the trials.">
Your browsing history, a record of sites you've visited using Thorium on this device.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_TOPICS_DATA_USAGE" desc="TOPICS API Bullet 2 of 3 that appear beneath the “Your interests as estimated by Chrome” subtitle. We break the description into the 3 pieces users most care about: 1) what data, 2) why this data, 3) what can I do about it? * “How we use this data:” is bold and serves as a label to help people skimming the page. * “estimate your interests”: Topics of interest include things like “Live comedy” and “Rock music”. Chrome estimates these interests based on the sites users visit. Its an “estimation”, and we dont want to suggest that we know with certainty the users interests. Avoid words like “guess”, “establish”, “define”, etc. (in place of “estimate”).">
Thorium can estimate your interests. Later, a site you visit can ask Thorium to see your interests in order to personalize the ads you see.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_TOPICS_DATA_MANAGEMENT" desc="TOPICS API Bullet 3 of 3 that appear beneath the “Your interests as estimated by Chrome” subtitle. We break the description into the 3 pieces users most care about: 1) what data, 2) why this data, 3) what can I do about it? * “How you can manage your data:” is bold and serves as a label to help people skimming the page. * “To protect your privacy”: Today, most data is kept for long periods of time. This new Topics API doesnt retain estimated topics for more than 3 weeks. The only reason for this feature is to protect the users privacy. * “auto”: isnt strictly necessary, but it conveys that this feature is an ongoing part of the service. This isnt describing, for example, a one-time deletion. * “older than 4 weeks”: Were trying to convey a rolling delete. Imagine a user opens a browser for the very first time. As the user browses, Chrome will estimate up to 5 topics of interest in the first week. In the second week, Chrome will estimate up to 5 additional topics of interest. The same for the third week, for a total of 15 potential interests. In week 4, Chrome will automatically delete the 5 interests from week 1 so that there arent ever more than 15 topics associated with a user at any given time. * “interests can refresh”: If a user loves horror films and reads about them for months on end, the interest “Horror movies” might get deleted and refreshed in the same week, so that “Horror movies” doesnt ever disappear from the users list of interests. * “Or you can…”: A user might love horror movies but cant stand the idea of seeing ads about horror movies (because even the visuals will ruin the surprise of opening night). In this case, the user can remove “Horror movies” from the list of interests Chrome will consider. This removal remains in place indefinitely. Note that the user might still see ads about Horror movies from different ad networks or by other means than Chromes “Browser-based ad personalization” setting.">
To protect your privacy, we auto-delete your interests that are older than 4 weeks. As you keep browsing, an interest might appear on the list again. Or you can remove interests you don't want Thorium to consider.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_FLEDGE_DATA_TYPES" desc="FLEDGE API Bullet 1 of 3 that appear beneath the “Sites you visit that define your interests” subtitle. We break the description into the 3 pieces users most care about: 1) what data, 2) why this data, 3) what can I do about it? * “What data is used:” is bold and serves as a label to help people skimming the page. * “Your browsing history”: The users browsing history is available beneath the “History” menu at Chromes top level. This content taken in isolation is somewhat misleading. With FLEDGE, a site can store information in Chrome about the users visit to their site. For example, the site might store “running_shoes_red_size_35” to indicate that the user showed interest in a particular shoe. Were OK with the simplification in this bullet because 1) we explain it in the next bullet and 2) we want the user to understand that at the top level, both Topics &amp; Fledge are based on the same thing and that is the users browsing history.">
Your browsing history, a record of sites you've visited using Thorium on this device.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_LEARN_MORE_DIALOG_FLEDGE_DATA_USAGE" desc="FLEDGE API Bullet 2 of 3 that appear beneath the “Sites you visit that define your interests” subtitle. We break the description into the 3 pieces users most care about: 1) what data, 2) why this data, 3) what can I do about it? * “How we use this data:” is bold and serves as a label to help people skimming the page. With FLEDGE, a site can store information in Chrome about the users visit to their site. For example, the site might store “running_shoes_red_size_35” to indicate that the user showed interest in a particular shoe. Were OK with the simplification in this bullet because 1) we explain it in the next bullet and 2) we want the user to understand that at the top level, both Topics &amp; Fledge are based on the same thing and that is the users browsing history. * “Later”: is important to convey the passage of time. We dont want to convey how much time (it could be tiny). Whats important is that the user understands this is essentially a two-step process. They browse, and Chrome might estimate their interests as they do so. At a later point when they continue to visit a site, thats when the estimated interests might come into play.">
Sites can store information with Thorium about your interests. For example, if you visit a site to buy shoes for a marathon, the site might define your interest as running marathons. Later, if you visit a different site to register for a race, that site can show you an ad for running shoes based on your interests.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_DESCRIPTION" desc="A paragraph beneath the card title. Note that this paragraph is written so that it describes both the Topics API and the FLEDGE API. Some things are described slightly differently for this reason. Version 1 of 3 of this paragraph. 1) The first line is written with the assumption that the user a) has Privacy Sandbox trials turned on and b) has been randomly selected by Chrome to be in an active experiment. As a result of both conditions, this user should have data on this page (a list of interests and a list of sites). 2) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user has the Privacy Sandbox trials turned on but they havent been randomly selected to be in a trial. 3) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user doesnt have the Privacy Sandbox trials turned on. * “browsing history”: “a record of sites youve visited using Chrome on this device.” * “affects the ads you see and the interests as estimated below”: browsing history leads to Chrome establishing user interests leads to 1) the ads you see are different, and 2) the list of things on this page changes based on what Chrome establishes.* “To protect your privacy”: Today, most data is kept for long periods of time. This new Topics API doesnt retain estimated topics for more than 3 weeks. The only reason for this feature is to protect the users privacy. * “auto”: isnt strictly necessary, but it conveys that this feature is an ongoing part of the service. This isnt describing, for example, a one-time deletion. * “rolling basis each month”: Information associated with Topics and FLEDGE are deleted on a rolling basis at least once per month. Its simpler to talk about “once per month” rather than 3 weeks for Topics and 4 weeks for FLEDGE. * “Interests can refresh…”: We intend for this line to cover both Topics and FLEDGE. Its slightly messy, because there is a suggestion that this line is more about Topics than FLEDGE (“interests” is more prominent in the Topics subtitle).">
Your browsing history affects the ads you see and the interests as estimated below. To protect your privacy, Thorium auto-deletes your interests on a rolling basis each month. Interests can refresh unless you remove them.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_DESCRIPTION_TRIALS_OFF" desc="A paragraph beneath the card title. Note that this paragraph is written so that it describes both the Topics API and the FLEDGE API. Some things are described slightly differently for this reason. Version 2 of 3 of this paragraph. 1) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user has Privacy Sandbox trials turned on AND that theyve been randomly selected for a trial. 2) The first line is written with the assumption that the user 1) has Privacy Sandbox trials turned on but 2) has NOT been randomly selected by Chrome to be in an active experiment. This explains why the user doesnt have data shown on the page. 3) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user doesnt have the Privacy Sandbox trials turned on. * “browsing history”: “a record of sites youve visited using Chrome on this device.” * “affects the ads you see and the interests as estimated below”: browsing history leads to Chrome establishing user interests leads to 1) the ads you see are different, and 2) the list of things on this page changes based on what Chrome establishes. * “To protect your privacy”: Today, most data is kept for long periods of time. This new Topics API doesnt retain estimated topics for more than 3 weeks. The only reason for this feature is to protect the users privacy. * “auto”: isnt strictly necessary, but it conveys that this feature is an ongoing part of the service. This isnt describing, for example, a one-time deletion. * “rolling basis each month”: Information associated with Topics and FLEDGE are deleted on a rolling basis at least once per month. Its simpler to talk about “once per month” rather than 3 weeks for Topics and 4 weeks for FLEDGE.* “Interests can refresh…”: We intend for this line to cover both Topics and FLEDGE. Its slightly messy, because there is a suggestion that this line is more about Topics than FLEDGE (“interests” is more prominent in the Topics subtitle).">
When trials are on and if Thorium has randomly placed you in an active trial, your browsing history affects the ads you see and the interests as estimated below. To protect your privacy, Thorium deletes your interests on a rolling basis each month.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_DESCRIPTION_LISTS_EMPTY" desc="A paragraph beneath the card title. Note that this paragraph is written so that it describes both the Topics API and the FLEDGE API. Some things are described slightly differently for this reason. Version 3 of 3 of this paragraph. 1) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user has Privacy Sandbox trials turned on AND that theyve been randomly selected for a trial. 2) NOT THE CASE FOR THIS STRING: A different version of this first line is written for the case that a user has the Privacy Sandbox trials turned on but they havent been randomly selected to be in a trial. 3) The first line is written with the assumption that the user a) doesnt have Privacy Sandbox trials turned on. b) Because of this, they cant be randomly selected for a trial. This explains why the user doesnt have data shown on the page. * “browsing history”: “a record of sites youve visited using Chrome on this device.” * “affects the ads you see and the interests as estimated below”: browsing history leads to Chrome establishing user interests leads to 1) the ads you see are different, and 2) the list of things on this page changes based on what Chrome establishes. * “To protect your privacy”: Today, most data is kept for long periods of time. This new Topics API doesnt retain estimated topics for more than 3 weeks. The only reason for this feature is to protect the users privacy. * “auto”: isnt strictly necessary, but it conveys that this feature is an ongoing part of the service. This isnt describing, for example, a one-time deletion. * “rolling basis each month”: Information associated with Topics and FLEDGE are deleted on a rolling basis at least once per month. Its simpler to talk about “once per month” rather than 3 weeks for Topics and 4 weeks for FLEDGE. * “Interests can refresh…”: We intend for this line to cover both Topics and FLEDGE. Its slightly messy, because there is a suggestion that this line is more about Topics than FLEDGE (“interests” is more prominent in the Topics subtitle).">
If Thorium has randomly placed you in an active trial, your browsing history affects the ads you see and the interests as estimated below. To protect your privacy, Thorium deletes your interests on a rolling basis each month. Interests refresh unless you remove them.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_TOPICS_TITLE" desc="Title of the browser-based interests section of the 'ad personalization' dialog.">
Your interests as estimated by Thorium
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_TOPICS_LEARN_MORE_1" desc="First learn more description of the browser-based interests section of the 'ad personalization' dialog.">
Thorium can estimate your interests based on your browsing history from the last few weeks. This info stays on your device.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_TOPICS_LEARN_MORE_2" desc="Second learn more description of the browser-based interests section of the 'ad personalization' dialog.">
Later, a site you visit can ask Thorium to see your interests in order to personalize the ads you see. Thorium can share up to 3 interests.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_TOPICS_LEARN_MORE_3" desc="Third learn more description of the browser-based interests section of the 'ad personalization' dialog.">
To protect your privacy, we auto-delete your interests that are older than 4 weeks. As you keep browsing, an interest might appear on the list again. And if Thorium gets it wrong or you don't want to see certain ads, you can remove an interest.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_PERSONALIZATION_DIALOG_FLEDGE_LEARN_MORE_1" desc="First learn more description of the website-based interests section of the 'ad personalization' dialog.">
It's common for sites you visit to remember things you're interested in, to personalize your experience. Sites can also store information with Thorium about your interests.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_MEASUREMENT_DIALOG_DESCRIPTION" desc="A description of the Ad measurement API. * “Ad measurement” is the name of an API in this context. We dont use “API” with the user, but they need to know that there is something called “A measurement” and what it does. * “sites you visit”: call the API to get information. The actor is the site, not Chrome. * “restricts cross-site tracking”: Today, with 3rd-party cookies, ad measurement technologies can inadvertently (and intentionally) share considerable information from one site to another). This feature restricts that sharing in order to improve the users privacy.">
Ad measurement allows sites you visit to request information from Thorium that helps the site measure the performance of their ads. Ad measurement restricts cross-site tracking by transferring as little information as possible between sites.
</message>
<message name="IDS_SETTINGS_PRIVACY_SANDBOX_AD_MEASUREMENT_DIALOG_DESCRIPTION_TRIALS_OFF" desc="A description of the Ad measurement API. * “Ad measurement” is the name of an API in this context. We dont use “API” with the user, but they need to know that there is something called “A measurement” and what it does. * “sites you visit”: call the API to get information. The actor is the site, not Chrome. * “restricts cross-site tracking”: Today, with 3rd-party cookies, ad measurement technologies can inadvertently (and intentionally) share considerable information from one site to another). This feature restricts that sharing in order to improve the users privacy.">
When trials are on, Ad measurement allows sites you visit to request information from Thorium that helps the site measure the performance of their ads. Ad measurement restricts cross-site tracking by transferring as little information as possible between sites.
</message>
<!-- Safety check -->
<message name="IDS_SETTINGS_SAFETY_CHECK_PARENT_PRIMARY_LABEL_BEFORE" desc="This text describes what the safety check is. (It's an area of the Settings page where users can quickly check whether their safety-related settings are fully protecting them.)">
Thorium can help keep you safe from data breaches, bad extensions, and more
</message>
<message name="IDS_SETTINGS_SAFETY_CHECK_UPDATES_FAILED_OFFLINE" desc="This text describes that Chromium cannot check for updates because there currently is no internet connection.">
Thorium can't check for updates. Try checking your internet connection.
</message>
<message name="IDS_SETTINGS_SAFETY_CHECK_UPDATES_FAILED" desc="This text describes that Chromium cannot update due to an unknown error.">
Thorium didn't update, something went wrong. <ph name="BEGIN_LINK">&lt;a target="_blank" href="$1"&gt;</ph>Fix Thorium update problems and failed updates.<ph name="END_LINK">&lt;/a&gt;</ph>
</message>
<message name="IDS_SETTINGS_SAFETY_CHECK_UPDATES_UNKNOWN" desc="This text displays the installed version of Chromium when it is not possible to check for updates on non-Chrome branded browsers.">
Thorium version <ph name="PRODUCT_VERSION">$1<ex>15.0.865.0</ex></ph> is installed
</message>
<message name="IDS_SETTINGS_SAFETY_CHECK_PASSWORDS_SIGNED_OUT" desc="This text points out that the password check can only run when the user is signed in.">
Thorium can't check your passwords because you're not signed in
</message>
<message name="IDS_SETTINGS_SAFETY_CHECK_SAFE_BROWSING_DISABLED" desc="This text points out that Safe Browsing is disabled and that the user is not protected.">
Safe Browsing is off. Thorium recommends turning it on.
</message>
<!-- Safe Browsing -->
<message name="IDS_SETTINGS_SAFEBROWSING_ENHANCED_BULLET_TWO" desc="Second bullet point under the safe browsing enhanced protection mode">
Keeps you safe on Thorium and may be used to improve your security in other Google apps when you are signed in
</message>
<message name="IDS_SETTINGS_SAFEBROWSING_STANDARD_BULLET_TWO" desc="First bullet point under the safe browsing standard protection mode">
Checks URLs with a list of unsafe sites stored in Thorium. If a site tries to steal your password, or when you download a harmful file, Thorium may also send URLs, including bits of page content, to Safe Browsing.
</message>
<!-- People Page -->
<message name="IDS_SETTINGS_SYNC_DISCONNECT_DELETE_PROFILE_WARNING_WITH_COUNTS_SINGULAR" desc="Warning message displayed in the Sign out of Chrome dialog that indicates profile browsing data will be removed from the device.">
This will delete 1 item from this device. To retrieve your data later, sign in to Thorium as <ph name="USER_EMAIL">$1<ex>foo@example.com</ex></ph>.
</message>
<message name="IDS_SETTINGS_SYNC_DISCONNECT_DELETE_PROFILE_WARNING_WITH_COUNTS_PLURAL" desc="Warning message displayed in the Sign out of Chrome dialog that indicates profile browsing data will be removed from the device.">
This will delete <ph name="ITEMS_COUNT">$1<ex>66</ex></ph> items from this device. To retrieve your data later, sign in to Thorium as <ph name="USER_EMAIL">$2<ex>foo@example.com</ex></ph>.
</message>
<message name="IDS_SETTINGS_SYNC_DISCONNECT_DELETE_PROFILE_WARNING_WITHOUT_COUNTS" desc="Warning message displayed in the Sign out of Chrome dialog that indicates profile browsing data will be removed from the device.">
This will delete your browsing data from this device. To retrieve your data later, sign in to Thorium as <ph name="USER_EMAIL">$1<ex>foo@example.com</ex></ph>.
</message>
<if expr="not chromeos_ash">
<message name="IDS_SETTINGS_CUSTOMIZE_YOUR_CHROME_PROFILE" desc="Label of the link that takes you to the page to customize your chrome profile.">
Customize your Thorium profile
</message>
<message name="IDS_SETTING_NAME_YOUR_PROFILE" desc="Title of the edit local profile name section on the manage profile page.">
Name your Thorium profile
</message>
</if>
<message name="IDS_SETTINGS_PEOPLE_SIGN_IN_PROMPT_SECONDARY_WITH_ACCOUNT" desc="The secondary text displayed to prompt users to enable sync for an account that is alredy present in Chromium.">
Sync and personalize Thorium across your devices
</message>
<if expr="chromeos_ash">
<message name="IDS_SETTINGS_ACCOUNT_MANAGER_DESCRIPTION_V2" desc="Description of the Account Manager Settings page. Shown just below the title of the page.">
You can manage your signed-in Google Accounts. Your Google Accounts are used for Thorium browser, Play Store, Gmail, and more. If you want to add an account for someone else, like a family member, add a new person to your <ph name="DEVICE_TYPE">$1<ex>Chromebook</ex></ph> instead. <ph name="LINK_BEGIN">&lt;a&gt;</ph>Learn more<ph name="LINK_END">&lt;/a&gt;</ph>
</message>
</if>
<!-- Sync Page -->
<message name="IDS_SETTINGS_SYNC_DATA_ENCRYPTED_TEXT" desc="Text alerting the user that synced data is encrypted.">
For added security, Thorium will encrypt your data.
</message>
<message name="IDS_SETTINGS_SYNC_DISCONNECT_TITLE" desc="The title of the dialog to stop syncing and sign out.">
Sign out of Thorium?
</message>
<message name="IDS_DRIVE_SUGGEST_PREF_DESC" desc="The documentation string of the 'Show Drive Results in Omnibox' - full description sentence">
Thorium will access your Drive to make suggestions in the address bar
</message>
<message name="IDS_SETTINGS_SYNC_SIGN_IN_PROMPT_WITH_NO_ACCOUNT" desc="The text displayed to prompt users to sign in to Chromium.">
Sign in to sync and personalize Thorium across your devices
</message>
<!-- Autofill Assistant settings -->
<message name="IDS_SETTINGS_AUTOFILL_ASSISTANT_PREF" translateable="false" desc="The documentation string of the 'Use Google Assistant' preference to help with automated flows on the web">
Google Assistant in Thorium
</message>
<!-- Languages Page -->
<if expr="is_win">
<message name="IDS_SETTINGS_LANGUAGES_IS_DISPLAYED_IN_THIS_LANGUAGE" desc="The label for a language that is currently used as the UI display language.">
This language is used to display the Thorium UI
</message>
<message name="IDS_SETTINGS_LANGUAGES_DISPLAY_IN_THIS_LANGUAGE" desc="The label used for a button that changes the UI language.">
Display Thorium in this language
</message>
</if>
<!-- System Page -->
<if expr="not chromeos_ash">
<message name="IDS_SETTINGS_SYSTEM_BACKGROUND_APPS_LABEL" desc="Label for the checkbox to allow apps to run in the background, when Chrome is closed.">
Continue running background apps when Thorium is closed
</message>
</if>
<!-- Reset Page -->
<message name="IDS_SETTINGS_RESET_PROFILE_FEEDBACK" desc="Feedback label in the Reset Profile Settings dialog">
Help make Thorium better by reporting the <ph name="BEGIN_LINK">&lt;a is="action-link" target="_blank"&gt;</ph>current settings<ph name="END_LINK">&lt;/a&gt;</ph>
</message>
</grit-part>

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,10 @@
COMPANY_FULLNAME=The Chromium Authors and Alex313031
COMPANY_SHORTNAME=The Chromium Authors and Alex313031
PRODUCT_FULLNAME=Thorium
PRODUCT_SHORTNAME=Thorium
PRODUCT_INSTALLER_FULLNAME=Thorium Installer
PRODUCT_INSTALLER_SHORTNAME=Thorium Installer
COPYRIGHT=Copyright @LASTCHANGE_YEAR@ The Chromium Authors and Alex313031. All rights reserved.
MAC_BUNDLE_ID=org.chromium.Thorium
MAC_CREATOR_CODE=Cr24
MAC_TEAM_ID=

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 792 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.2 KiB

View file

@ -0,0 +1,639 @@
/* XPM */
static char * product_logo_256_xpm[] = {
"256 256 380 2",
" c None",
". c #1967D2",
"+ c #236BD4",
"@ c #1761C6",
"# c #165DBE",
"$ c #1354AE",
"% c #1251A7",
"& c #3261B2",
"* c #557CC8",
"= c #6389D4",
"- c #7499E3",
"; c #84A6E9",
"> c #548DEA",
", c #1865CE",
"' c #155ABA",
") c #114FA5",
"! c #0D428B",
"~ c #07316A",
"{ c #04224F",
"] c #000000",
"^ c #414D61",
"/ c #5A6A84",
"( c #7286A6",
"_ c #88A0C5",
": c #9AB4DE",
"< c #ABC8F6",
"[ c #AECBFA",
"} c #669DF6",
"| c #3575DA",
"1 c #1457B2",
"2 c #0E4591",
"3 c #062B5E",
"4 c #54637B",
"5 c #798DAF",
"6 c #95AED7",
"7 c #ABC7F6",
"8 c #5C94EF",
"9 c #1863CA",
"0 c #093776",
"a c #00030F",
"b c #191E28",
"c c #61728E",
"d c #8AA1C7",
"e c #A8C4F1",
"f c #427EE0",
"g c #1356B1",
"h c #093878",
"i c #040508",
"j c #657693",
"k c #92ABD3",
"l c #6299F3",
"m c #206AD4",
"n c #0F4999",
"o c #031B40",
"p c #353F4F",
"q c #8096BA",
"r c #4D87E6",
"s c #1760C5",
"t c #0D438E",
"u c #01102C",
"v c #232B37",
"w c #788CAD",
"x c #A7C3F0",
"y c #649BF5",
"z c #2E71D8",
"A c #010615",
"B c #222A36",
"C c #788CAE",
"D c #568EEB",
"E c #104A9B",
"F c #01112D",
"G c #8399BD",
"H c #3877DC",
"I c #1457B4",
"J c #042451",
"K c #49576D",
"L c #96AFD8",
"M c #5E96F1",
"N c #0A3B7E",
"O c #7184A4",
"P c #AAC7F5",
"Q c #4681E2",
"R c #1458B5",
"S c #031C43",
"T c #042552",
"U c #073470",
"V c #042554",
"W c #404C5F",
"X c #97B0DA",
"Y c #629AF3",
"Z c #256CD5",
"` c #1966CF",
" . c #0E4692",
".. c #031F48",
"+. c #0A3F85",
"@. c #0F51A7",
"#. c #135CBD",
"$. c #1668D2",
"%. c #196FE0",
"&. c #1A73E8",
"*. c #135DBD",
"=. c #7D92B5",
"-. c #4F89E7",
";. c #08336E",
">. c #011432",
",. c #0B428B",
"'. c #1259B6",
"). c #186BD8",
"!. c #5C6C86",
"~. c #3072D8",
"{. c #155BBB",
"]. c #011331",
"^. c #1460C3",
"/. c #1971E4",
"(. c #A1BCE8",
"_. c #5991ED",
":. c #1457B3",
"<. c #052A5D",
"[. c #1157B3",
"}. c #9AB4DD",
"|. c #3E7BDE",
"1. c #062E65",
"2. c #135DBE",
"3. c #062F65",
"4. c #8FA7CF",
"5. c #5F96F1",
"6. c #052E65",
"7. c #4883E3",
"8. c #1A72E6",
"9. c #266DD5",
"0. c #0A4188",
"a. c #186DDC",
"b. c #91A9D1",
"c. c #538CE9",
"d. c #135CBC",
"e. c #3474DA",
"f. c #155BBA",
"g. c #07336F",
"h. c #186CDB",
"i. c #A3BEEB",
"j. c #5B93EE",
"k. c #0C4793",
"l. c #AAC6F4",
"m. c #1865CF",
"n. c #08326C",
"o. c #1155AF",
"p. c #60718D",
"q. c #6199F3",
"r. c #0E4592",
"s. c #000002",
"t. c #125AB9",
"u. c #8096B9",
"v. c #4C86E5",
"w. c #01102A",
"x. c #145FC1",
"y. c #145FC2",
"z. c #9BB5DF",
"A. c #2C70D7",
"B. c #031B41",
"C. c #558DEA",
"D. c #0A3B7D",
"E. c #3877DB",
"F. c #5E95F0",
"G. c #042350",
"H. c #4A576D",
"I. c #4580E1",
"J. c #0F4A9B",
"K. c #869CC1",
"L. c #216AD4",
"M. c #333D4E",
"N. c #A8C4F2",
"O. c #0E4590",
"P. c #659CF6",
"Q. c #1762C8",
"R. c #010D24",
"S. c #5890EC",
"T. c #3C7ADD",
"U. c #28303D",
"V. c #ABC7F5",
"W. c #1C68D3",
"X. c #104B9C",
"Y. c #4882E3",
"Z. c #475469",
"`. c #1356B2",
" + c #98B1DA",
".+ c #528BE9",
"++ c #6D809F",
"@+ c #3173D9",
"#+ c #1863CB",
"$+ c #01081A",
"%+ c #5A92EE",
"&+ c #1251A8",
"*+ c #417DE0",
"=+ c #0A397A",
"-+ c #687A97",
";+ c #6098F2",
">+ c #01112C",
",+ c #333D4D",
"'+ c #4B85E5",
")+ c #296ED6",
"!+ c #0F4897",
"~+ c #8197BB",
"{+ c #61728D",
"]+ c #3777DB",
"^+ c #000103",
"/+ c #252D3A",
"(+ c #5D94F0",
"_+ c #155CBD",
":+ c #437FE1",
"<+ c #8EA6CE",
"[+ c #0D438D",
"}+ c #4F88E7",
"|+ c #093572",
"1+ c #6A7D9B",
"2+ c #05295B",
"3+ c #526179",
"4+ c #578FEC",
"5+ c #2D3644",
"6+ c #3A79DC",
"7+ c #A5C0ED",
"8+ c #4782E3",
"9+ c #042553",
"0+ c #9DB8E3",
"a+ c #639AF4",
"b+ c #155AB8",
"c+ c #518AE8",
"d+ c #3F7CDF",
"e+ c #5F97F1",
"f+ c #8FA8CF",
"g+ c #4A84E4",
"h+ c #276DD5",
"i+ c #A4BFEC",
"j+ c #042452",
"k+ c #576780",
"l+ c #1150A7",
"m+ c #889FC4",
"n+ c #072F67",
"o+ c #4D5B71",
"p+ c #0E4693",
"q+ c #93ACD5",
"r+ c #010C24",
"s+ c #0A0E14",
"t+ c #000105",
"u+ c #62738F",
"v+ c #1C59B3",
"w+ c #343E4E",
"x+ c #20529F",
"y+ c #7E94B7",
"z+ c #5389E3",
"A+ c #2F589C",
"B+ c #7589A9",
"C+ c #5A8FE5",
"D+ c #010A1F",
"E+ c #0A4088",
"F+ c #10141B",
"G+ c #A3BEEA",
"H+ c #3E65A5",
"I+ c #7589AA",
"J+ c #6196EC",
"K+ c #101F36",
"L+ c #4A73B6",
"M+ c #07336E",
"N+ c #649AF2",
"O+ c #233A60",
"P+ c #5686D3",
"Q+ c #91ABD6",
"R+ c #3A5D94",
"S+ c #5E7396",
"T+ c #6297ED",
"U+ c #1B2F4E",
"V+ c #1C304F",
"W+ c #A2C0F1",
"X+ c #5786D4",
"Y+ c #7E9ED6",
"Z+ c #456CAC",
"`+ c #4C70AC",
" @ c #AAC8FA",
".@ c #325081",
"+@ c #93B7F5",
"@@ c #6094E9",
"#@ c #22395D",
"$@ c #709DE9",
"%@ c #ADCAFA",
"&@ c #5A8BDB",
"*@ c #9DBFF9",
"=@ c #5685D2",
"-@ c #5686D2",
";@ c #7FABF7",
">@ c #507CC4",
",@ c #0A4087",
"'@ c #A5C5F9",
")@ c #8CB3F8",
"!@ c #6EA1F6",
"~@ c #ABC9FA",
"{@ c #96BAF8",
"]@ c #052A5C",
"^@ c #76A6F7",
"/@ c #5A8BDA",
"(@ c #A0C1F9",
"_@ c #314F80",
":@ c #83AEF7",
"<@ c #456CAB",
"[@ c #6A9FF6",
"}@ c #A6C5F9",
"|@ c #1B2E4D",
"1@ c #5786D3",
"2@ c #8EB4F8",
"3@ c #3A5C94",
"4@ c #ACC9FA",
"5@ c #233A5F",
"6@ c #99BCF9",
"7@ c #4A73B7",
"8@ c #79A8F7",
"9@ c #446BA9",
"0@ c #0B1629",
"a@ c #0D192D",
"b@ c #446BAA",
"c@ c #A2C2F9",
"d@ c #6195EA",
"e@ c #446AA9",
"f@ c #86AFF7",
"g@ c #4973B5",
"h@ c #1C3050",
"i@ c #4A74B7",
"j@ c #A9C7FA",
"k@ c #5584CF",
"l@ c #395A90",
"m@ c #010307",
"n@ c #081222",
"o@ c #5585D1",
"p@ c #91B7F8",
"q@ c #37578B",
"r@ c #0D1A2E",
"s@ c #507DC5",
"t@ c #72A4F7",
"u@ c #466DAD",
"v@ c #2F4B7A",
"w@ c #010204",
"x@ c #325082",
"y@ c #4770B1",
"z@ c #5787D5",
"A@ c #9ABDF9",
"B@ c #649BF2",
"C@ c #4167A3",
"D@ c #325182",
"E@ c #243B61",
"F@ c #28426C",
"G@ c #355487",
"H@ c #4268A6",
"I@ c #5B8DDE",
"J@ c #7CAAF7",
"K@ c #5C8EDF",
"L@ c #598AD8",
"M@ c #6298EE",
"N@ c #A5C4F9",
"O@ c #89B1F8",
"P@ c #6BA0F6",
"Q@ c #94B9F8",
"R@ c #75A5F7",
"S@ c #9EBFF9",
"T@ c #80ACF7",
"U@ c #679DF6",
"V@ c #A7C6F9",
"W@ c #8EB5F8",
"X@ c #6EA2F6",
"Y@ c #7AA8F7",
"Z@ c #A9C8FA",
"`@ c #92B7F8",
" # c #73A4F7",
".# c #9BBDF9",
"+# c #89B2F8",
"@# c #679EF6",
"## c #84AEF7",
"$# c #A7C6FA",
"%# c #6FA2F6",
"&# c #A2C3F9",
"*# c #9BBEF9",
"=# c #6CA0F6",
"-# c #9EC0F9",
";# c #A3C3F9",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ",
" + . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . @ # # $ % % % % & * * = - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ; ",
" > . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . , ' ) ! ~ { ] ] ] ] ] ] ] ] ] ] ] ] ] ] ^ / ( _ : < [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } | . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . , 1 2 3 ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 4 5 6 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } 8 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 % 0 a ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] b c d e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } f . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . g h ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] i j k [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } l m . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 n o ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] p q e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } r . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . s t u ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] v w x [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } y z . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 t A ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] B C e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } D . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . , E F ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] v G 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } H . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . I J ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] K L [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } M . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 N ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] O P [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } Q . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . R S ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] T U U U U U U V ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] W X [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } Y Z . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . ` .] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ..+.@.#.$.%.&.&.&.&.&.&.&.&.&.&.%.$.*.@.+...] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] =.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } -.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . @ ;.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.,.'.).&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.).'.,.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] !.e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } ~.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . {.{ ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ].,.^./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.^.,.].] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] W (.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } _.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . :.F ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] <.[.%.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.[.<.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] v }.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } |.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . % ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 1.2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.3.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] v 4.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } 5.m . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . % ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 6.2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.6.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] d [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } 7.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . % ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.[.8.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.8.[.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] d [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } y 9.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . % ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 0.a.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.a.0.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] b.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } c.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . :.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.d.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.d.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] v }.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } e.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . f.F ] ] ] ] ] ] ] ] ] ] ] ] ] ] g.h.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.h.g.] ] ] ] ] ] ] ] ] ] ] ] ] ] v i.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } j.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . @ { ] ] ] ] ] ] ] ] ] ] ] ] ] ] k./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.k.] ] ] ] ] ] ] ] ] ] ] ] ] ] W l.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } f . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . m.n.] ] ] ] ] ] ] ] ] ] ] ] ] ] o.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.o.] ] ] ] ] ] ] ] ] ] ] ] ] ] p.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } q.m . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . r.] ] ] ] ] ] ] ] ] ] ] ] ] s.t.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.t.s.] ] ] ] ] ] ] ] ] ] ] ] ] u.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } v.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . I ] ] ] ] ] ] ] ] ] ] ] ] ] w.x.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.y.w.] ] ] ] ] ] ] ] ] ] ] ] ] z.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } y A.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 B.] ] ] ] ] ] ] ] ] ] ] ] s.x.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.y.s.] ] ] ] ] ] ] ] ] ] ] ] W 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } C.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . D.] ] ] ] ] ] ] ] ] ] ] ] ] t.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.t.] ] ] ] ] ] ] ] ] ] ] ] ] ( [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } E.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . :.] ] ] ] ] ] ] ] ] ] ] ] ] o.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.o.] ] ] ] ] ] ] ] ] ] ] ] ] : [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } F.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . , G.] ] ] ] ] ] ] ] ] ] ] ] k.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.k.] ] ] ] ] ] ] ] ] ] ] ] H.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } I.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . J.] ] ] ] ] ] ] ] ] ] ] ] g./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.g.] ] ] ] ] ] ] ] ] ] ] ] K.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y L.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 F ] ] ] ] ] ] ] ] ] ] ] >.h.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.h.>.] ] ] ] ] ] ] ] ] ] ] M.N.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } -.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . O.] ] ] ] ] ] ] ] ] ] ] ] d.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.d.] ] ] ] ] ] ] ] ] ] ] ] w [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } P.~.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . Q.R.] ] ] ] ] ] ] ] ] ] ] 0.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.0.] ] ] ] ] ] ] ] ] ] ] v e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } S.. . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2 ] ] ] ] ] ] ] ] ] ] ] >.a.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.a.>.] ] ] ] ] ] ] ] ] ] ] w [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T.. . . . . . . . . . . . . . . . . . . . . . . . . . . 9 F ] ] ] ] ] ] ] ] ] ] ] [.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.[.] ] ] ] ] ] ] ] ] ] ] U.V.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } M W.. . . . . . . . . . . . . . . . . . . . . . . . . . X.] ] ] ] ] ] ] ] ] ] ] 6.8.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.8.6.] ] ] ] ] ] ] ] ] ] ] K.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y.. . . . . . . . . . . . . . . . . . . . . . . . . . S ] ] ] ] ] ] ] ] ] ] ] 2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.] ] ] ] ] ] ] ] ] ] ] Z.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y 9.. . . . . . . . . . . . . . . . . . . . . . . . `.] ] ] ] ] ] ] ] ] ] ] 1.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.1.] ] ] ] ] ] ] ] ] ] ] +[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } .+. . . . . . . . . . . . . . . . . . . . . . . . D.] ] ] ] ] ] ] ] ] ] ] 2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.] ] ] ] ] ] ] ] ] ] ] ++[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } @+. . . . . . . . . . . . . . . . . . . . . . #+$+] ] ] ] ] ] ] ] ] ] <.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.<.] ] ] ] ] ] ] ] ] ] v 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } %+. . . . . . . . . . . . . . . . . . . . . . &+] ] ] ] ] ] ] ] ] ] ] [.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.[.] ] ] ] ] ] ] ] ] ] ] k [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } *+. . . . . . . . . . . . . . . . . . . . . =+] ] ] ] ] ] ] ] ] ] ].%.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.].] ] ] ] ] ] ] ] ] ] -+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ;+m . . . . . . . . . . . . . . . . . . . , >+] ] ] ] ] ] ] ] ] ] ,.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.,.] ] ] ] ] ] ] ] ] ] ,+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } '+. . . . . . . . . . . . . . . . . . . R ] ] ] ] ] ] ] ] ] ] ] ^.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.^.] ] ] ] ] ] ] ] ] ] ] : [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y )+. . . . . . . . . . . . . . . . . . !+] ] ] ] ] ] ] ] ] ] >./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.>.] ] ] ] ] ] ] ] ] ] ~+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } > . . . . . . . . . . . . . . . . . . ;.] ] ] ] ] ] ] ] ] ] ,.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.,.] ] ] ] ] ] ] ] ] ] {+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ]+. . . . . . . . . . . . . . . . . ^+] ] ] ] ] ] ] ] ] ] '.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.'.] ] ] ] ] ] ] ] ] ] /+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } (+. . . . . . . . . . . . . . . . _+] ] ] ] ] ] ] ] ] ] ] ).&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.).] ] ] ] ] ] ] ] ] ] ] (.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } :+. . . . . . . . . . . . . . . % ] ] ] ] ] ] ] ] ] ] ..&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&...] ] ] ] ] ] ] ] ] ] <+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y m . . . . . . . . . . . . . . [+] ] ] ] ] ] ] ] ] ] +.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.+.] ] ] ] ] ] ] ] ] ] =.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } }+. . . . . . . . . . . . . . |+] ] ] ] ] ] ] ] ] ] @.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.@.] ] ] ] ] ] ] ] ] ] 1+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y ~.. . . . . . . . . . . . . 2+] ] ] ] ] ] ] ] ] ] *.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.*.] ] ] ] ] ] ] ] ] ] 3+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 4+. . . . . . . . . . . . . ] ] ] ] ] ] ] ] ] ] ] $.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.$.] ] ] ] ] ] ] ] ] ] 5+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 6+. . . . . . . . . . . #+] ] ] ] ] ] ] ] ] ] ] %.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.] ] ] ] ] ] ] ] ] ] ] [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } M . . . . . . . . . . . # ] ] ] ] ] ] ] ] ] ] ] &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.] ] ] ] ] ] ] ] ] ] ] 7+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 8+. . . . . . . . . . # ] ] ] ] ] ] ] ] ] ] V &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.9+] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } a+9.. . . . . . . . . b+] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } c+. . . . . . . . . % ] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ~.. . . . . . . . % ] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } %+. . . . . . . . % ] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] d [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } d+. . . . . . . % ] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] d [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } e+m . . . . . . R ] ] ] ] ] ] ] ] ] ] U &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.U ] ] ] ] ] ] ] ] ] ] f+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } g+. . . . . . # ] ] ] ] ] ] ] ] ] ] 9+&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.9+] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y h+. . . . . # ] ] ] ] ] ] ] ] ] ] ] &.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.] ] ] ] ] ] ] ] ] ] ] 0+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } > . . . . . 9 ] ] ] ] ] ] ] ] ] ] ] %.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.] ] ] ] ] ] ] ] ] ] ] i+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } | . . . . . ] ] ] ] ] ] ] ] ] ] ] $.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.$.] ] ] ] ] ] ] ] ] ] ] [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 8 . . . . . j+] ] ] ] ] ] ] ] ] ] *.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.*.] ] ] ] ] ] ] ] ] ] W [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } f . . . . ;.] ] ] ] ] ] ] ] ] ] @.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.@.] ] ] ] ] ] ] ] ] ] k+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } l m . . . ! ] ] ] ] ] ] ] ] ] ] +.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.+.] ] ] ] ] ] ] ] ] ] ( [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } r . . . l+] ] ] ] ] ] ] ] ] ] ..&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&...] ] ] ] ] ] ] ] ] ] m+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y z . . {.] ] ] ] ] ] ] ] ] ] ] ).&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.).] ] ] ] ] ] ] ] ] ] ] : [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } D . . m.] ] ] ] ] ] ] ] ] ] ] '.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.'.] ] ] ] ] ] ] ] ] ] ] 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } H . . n+] ] ] ] ] ] ] ] ] ] ,.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.,.] ] ] ] ] ] ] ] ] ] o+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } M . . p+] ] ] ] ] ] ] ] ] ] >./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.>.] ] ] ] ] ] ] ] ] ] C [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Q . I ] ] ] ] ] ] ] ] ] ] ] ^.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.^.] ] ] ] ] ] ] ] ] ] ] q+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y Z , r+] ] ] ] ] ] ] ] ] ] ,.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.,.] ] ] ] ] ] ] ] ] ] s+V.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } -.. 0 ] ] ] ] ] ] ] ] ] ] ].%.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.].] ] ] ] ] ] ] ] ] ] {+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ~.% ] ] ] ] ] ] ] ] ] ] ] [.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.[.] ] ] ] ] ] ] ] ] ] ] d [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } _.9 t+] ] ] ] ] ] ] ] ] ] <.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.<.] ] ] ] ] ] ] ] ] ] ] e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } |.=+] ] ] ] ] ] ] ] ] ] ] 2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.] ] ] ] ] ] ] ] ] ] ] u+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 5.v+] ] ] ] ] ] ] ] ] ] ] 1.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.1.] ] ] ] ] ] ] ] ] ] ] k [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 7.B.] ] ] ] ] ] ] ] ] ] ] 2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.] ] ] ] ] ] ] ] ] ] ] w+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } y x+] ] ] ] ] ] ] ] ] ] ] 6.8.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.8.6.] ] ] ] ] ] ] ] ] ] ] y+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } z+F ] ] ] ] ] ] ] ] ] ] ] [.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.[.] ] ] ] ] ] ] ] ] ] ] v e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } A+] ] ] ] ] ] ] ] ] ] ] >.a.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.a.>.] ] ] ] ] ] ] ] ] ] ] B+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } C+D+] ] ] ] ] ] ] ] ] ] ] E+&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.E+] ] ] ] ] ] ] ] ] ] ] F+G+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } H+] ] ] ] ] ] ] ] ] ] ] ] d.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.d.] ] ] ] ] ] ] ] ] ] ] ] I+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } J+K+] ] ] ] ] ] ] ] ] ] ] >.h.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.h.>.] ] ] ] ] ] ] ] ] ] ] v e [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } L+] ] ] ] ] ] ] ] ] ] ] ] g./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.M+] ] ] ] ] ] ] ] ] ] ] ] u.[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N+O+] ] ] ] ] ] ] ] ] ] ] ] k.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.k.] ] ] ] ] ] ] ] ] ] ] ] ^ 7 [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } P+] ] ] ] ] ] ] ] ] ] ] ] ] o.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.o.] ] ] ] ] ] ] ] ] ] ] ] ] Q+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } R+] ] ] ] ] ] ] ] ] ] ] ] ] t.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.t.] ] ] ] ] ] ] ] ] ] ] ] ] S+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+U+] ] ] ] ] ] ] ] ] ] ] ] s.x.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.x.s.] ] ] ] ] ] ] ] ] ] ] ] V+W+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } X+] ] ] ] ] ] ] ] ] ] ] ] ] w.x.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.x.w.] ] ] ] ] ] ] ] ] ] ] ] ] Y+[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Z+] ] ] ] ] ] ] ] ] ] ] ] ] s.t.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.t.s.] ] ] ] ] ] ] ] ] ] ] ] ] `+ @[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N+.@] ] ] ] ] ] ] ] ] ] ] ] ] ] o.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.o.] ] ] ] ] ] ] ] ] ] ] ] ] ] .@+@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } @@#@] ] ] ] ] ] ] ] ] ] ] ] ] ] k./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.k.] ] ] ] ] ] ] ] ] ] ] ] ] ] #@$@%@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } &@K+] ] ] ] ] ] ] ] ] ] ] ] ] ] g.h.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.h.M+] ] ] ] ] ] ] ] ] ] ] ] ] ] K+&@*@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } =@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.d.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.d.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] -@;@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } >@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ,@a.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.a.0.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >@} '@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } >@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.[.8.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.8.[.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >@} )@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } >@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 6.2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.6.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >@} !@~@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } >@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 1.2.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.2.1.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >@} } {@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } =@K+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ]@[.%.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.%.[.<.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] K+=@} } ^@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } &@#@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ].,.^./.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&./.^.,.].] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] #@/@} } } (@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } @@.@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] >.,.'.).&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.&.).'.,.>.] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] _@@@} } } :@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N+Z+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ..+.@.#.$.%.&.&.&.&.&.&.&.&.&.&.%.$.*.@.+...] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] <@N+} } } [@}@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } X+U+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] T U U U U U U V ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] |@1@} } } } } 2@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+R+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 3@T+} } } } } !@4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } P+O+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] 5@-@} } } } } } } 6@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N+7@K+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] K+L+N+} } } } } } } 8@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+9@0@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] a@b@T+} } } } } } } } } c@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } d@e@K+] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] K+b@d@} } } } } } } } } } f@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+g@|@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] h@i@T+} } } } } } } } } } } [@j@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } k@l@m@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] n@3@o@} } } } } } } } } } } } } } p@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+>@q@r@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] K+l@s@T+} } } } } } } } } } } } } } } t@4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N+1@u@v@] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] ] w@x@y@z@N+} } } } } } } } } } } } } } } } } } A@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } B@&@>@C@D@E@] ] ] ] ] ] ] ] ] ] ] ] ] ] F@G@H@>@I@} } } } } } } } } } } } } } } } } } } } } } J@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T+K@K@z@>@>@>@>@L@K@K@M@} } } } } } } } } } } } } } } } } } } } } } } } } } } } N@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } O@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } P@ @[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Q@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } R@%@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } S@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } U@'@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } )@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } !@~@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } {@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ^@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } (@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } :@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } [@V@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } W@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } X@4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 6@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } c@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } f@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } [@Z@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } `@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } #4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } .#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } J@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } N@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } +#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } P@ @[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Q@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } R@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } S@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } T@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } @#'@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } )@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } !@~@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } {@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ^@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } (@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } ##[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } [@$#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } W@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } %#4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } 6@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Y@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } &#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } f@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } [@ @[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } `@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } #4@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } *#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } J@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } '@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } +#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } =# @[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } } Q@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } } } } } R@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } } } } } } } } -#[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } } } } } } } } } } } T@[ [ [ [ [ [ [ [ [ [ [ [ [ [ [ [ ",
" } } } } } } } ;#[ [ [ [ [ [ ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" ",
" "};

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 792 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 9.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 54 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 10 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 538 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 538 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 432 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 596 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 809 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 809 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.5 KiB

View file

@ -0,0 +1,51 @@
// Copyright 2022 The Brave Authors and Alex313031. All rights reserved.
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this file,
// You can obtain one at http://mozilla.org/MPL/2.0/.
// Modified, Originally from https://github.com/brave/brave-core/blob/master/vector_icons/chrome/app/vector_icons/browser_tools.icon
CANVAS_DIMENSIONS, 32,
PATH_COLOR_ARGB, 0xFF, 0x1A, 0x73, 0xE8,
MOVE_TO, 25, 26.5f,
CUBIC_TO, 25, 25.67f, 24.33f, 25, 23.5f, 25,
LINE_TO, 8.5f, 25,
CUBIC_TO, 7.67f, 25, 7, 25.67f, 7, 26.5f,
CUBIC_TO, 7, 27.33f, 7.67f, 28, 8.5f, 28,
LINE_TO, 23.5f, 28,
CUBIC_TO, 24.33f, 28, 25, 27.33f, 25, 26.5f,
MOVE_TO, 25, 15.5f,
CUBIC_TO, 25, 14.67f, 24.33f, 14, 23.5f, 14,
LINE_TO, 8.5f, 14,
CUBIC_TO, 7.67f, 14, 7, 14.67f, 7, 15.5f,
CUBIC_TO, 7, 16.33f, 7.67f, 17, 8.5f, 17,
LINE_TO, 23.5f, 17,
CUBIC_TO, 24.33f, 17, 25, 16.33f, 25, 15.5f,
MOVE_TO, 23.5f, 6,
LINE_TO, 8.5f, 6,
CUBIC_TO, 7.67f, 6, 7, 5.33f, 7, 4.5f,
CUBIC_TO, 7, 3.67f, 7.67f, 3, 8.5f, 3,
LINE_TO, 23.5f, 3,
CUBIC_TO, 24.33f, 3, 25, 3.67f, 25, 4.5f,
CUBIC_TO, 25, 5.33f, 24.33f, 6, 23.5f, 6,
CLOSE
CANVAS_DIMENSIONS, 16,
PATH_COLOR_ARGB, 0xFF, 0x1A, 0x73, 0xE8,
MOVE_TO, 12.75f, 13,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, -0.75f, -0.75f,
H_LINE_TO, 4,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, 0, 1.5f,
R_H_LINE_TO, 8,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, 0.75f, -0.75f,
R_MOVE_TO, 0, -5,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, -0.75f, -0.75f,
H_LINE_TO, 4,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, 0, 1.5f,
R_H_LINE_TO, 8,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 0, 0.75f, -0.75f,
MOVE_TO, 12, 3.75f,
H_LINE_TO, 4,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 1, 0, -1.5f,
R_H_LINE_TO, 8,
R_ARC_TO, 0.75f, 0.75f, 0, 0, 1, 0, 1.5f,
CLOSE

View file

@ -0,0 +1,22 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
CANVAS_DIMENSIONS, 16,
CIRCLE, 8, 8, 8,
CLOSE,
NEW_PATH,
PATH_COLOR_ARGB, 0xFF, 0xFF, 0xFF, 0xFF,
MOVE_TO, 9, 8,
H_LINE_TO, 7,
V_LINE_TO, 4,
R_H_LINE_TO, 2,
R_V_LINE_TO, 4,
CLOSE,
R_MOVE_TO, 0, 4,
H_LINE_TO, 7,
R_V_LINE_TO, -2,
R_H_LINE_TO, 2,
R_V_LINE_TO, 2,
CLOSE

View file

@ -0,0 +1,18 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 24,
PATH_COLOR_ARGB, 0xFF, 0x1A, 0x73, 0xE8,
MOVE_TO, 12, 8,
R_ARC_TO, 2, 2, 0, 1, 0, 0, -4,
R_ARC_TO, 2, 2, 0, 0, 0, 0, 4,
CLOSE,
R_MOVE_TO, 0, 2,
R_ARC_TO, 2, 2, 0, 1, 0, 0, 4,
R_ARC_TO, 2, 2, 0, 0, 0, 0, -4,
CLOSE,
R_MOVE_TO, 0, 6,
R_ARC_TO, 2, 2, 0, 1, 0, 0, 4,
R_ARC_TO, 2, 2, 0, 0, 0, 0, -4,
CLOSE

View file

@ -0,0 +1,19 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 16,
PATH_COLOR_ARGB, 0xFF, 0x33, 0x67, 0xD6,
CIRCLE, 8, 8, 8,
CLOSE,
NEW_PATH,
PATH_COLOR_ARGB, 0xFF, 0xFF, 0xFF, 0xFF,
MOVE_TO, 6, 12,
R_H_LINE_TO, 4,
V_LINE_TO, 9,
R_H_LINE_TO, 2,
LINE_TO, 8, 4,
LINE_TO, 4, 9,
R_H_LINE_TO, 2,
R_V_LINE_TO, 3,
CLOSE

View file

@ -0,0 +1,20 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 16,
PATH_COLOR_ARGB, 0xFF, 0x87, 0xFF, 0xC5,
MOVE_TO, 4.13f, 1,
R_H_LINE_TO, 7.74f,
R_V_LINE_TO, 1.56f,
R_H_LINE_TO, -1.56f,
R_V_LINE_TO, 3.68f,
R_LINE_TO, 4.39f, 6.3f,
ARC_TO, 1.56f, 1.56f, 0, 0, 1, 13.44f, 15,
H_LINE_TO, 2.56f,
R_ARC_TO, 1.56f, 1.56f, 0, 0, 1, -1.26f, -2.47f,
R_LINE_TO, 4.39f, -6.3f,
R_V_LINE_TO, -3.68f,
H_LINE_TO, 4.13f,
V_LINE_TO, 1,
CLOSE

View file

@ -0,0 +1,23 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 24,
PATH_COLOR_ARGB, 0xFF, 0x87, 0xFF, 0xC5,
MOVE_TO, 7.02f, 3,
R_H_LINE_TO, 9.96f,
R_V_LINE_TO, 2,
R_H_LINE_TO, -2,
R_V_LINE_TO, 4.73f,
R_LINE_TO, 5.64f, 8.09f,
ARC_TO, 2, 2, 0, 0, 1, 19, 21,
H_LINE_TO, 5,
R_CUBIC_TO, -0.75f, 0, -1.44f, -0.42f, -1.78f, -1.09f,
R_CUBIC_TO, -0.34f, -0.67f, -0.28f, -1.47f, 0.16f, -2.08f,
R_LINE_TO, 5.65f, -8.09f,
V_LINE_TO, 5,
H_LINE_TO, 7.02f,
V_LINE_TO, 3,
CLOSE,
PATH_COLOR_ARGB, 0xFF, 0x87, 0xFF, 0xC5,
NEW_PATH

View file

@ -0,0 +1,53 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
STROKE, 3,
CAP_SQUARE,
MOVE_TO, 1.5, 8.5,
R_V_LINE_TO, 34,
R_H_LINE_TO, 45,
R_V_LINE_TO, -28,
R_MOVE_TO, -3, -3,
R_H_LINE_TO, -10,
R_V_LINE_TO, -3,
R_MOVE_TO, -3, -3,
R_H_LINE_TO, -10,
R_MOVE_TO, 15, 6,
R_H_LINE_TO, -18,
R_V_LINE_TO, -3,
R_MOVE_TO, -3, -3,
R_H_LINE_TO, -10,
NEW_PATH,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
STROKE, 2,
CAP_SQUARE,
MOVE_TO, 12, 35,
R_H_LINE_TO, 2,
R_MOVE_TO, 2, -2,
R_H_LINE_TO, 12,
R_MOVE_TO, 2, 2,
R_H_LINE_TO, 3,
R_MOVE_TO, 2, 2,
R_H_LINE_TO, 3,
MOVE_TO, 11, 21,
R_LINE_TO, 0, 0,
R_MOVE_TO, 0, 4,
R_LINE_TO, 0, 0,
R_MOVE_TO, 4, 0,
R_LINE_TO, 0, 0,
R_MOVE_TO, 0, -4,
R_LINE_TO, 0, 0,
R_MOVE_TO, -2, 2,
R_LINE_TO, 0, 0,
MOVE_TO, 33, 21,
R_LINE_TO, 0, 0,
R_MOVE_TO, 0, 4,
R_LINE_TO, 0, 0,
R_MOVE_TO, 4, 0,
R_LINE_TO, 0, 0,
R_MOVE_TO, 0, -4,
R_LINE_TO, 0, 0,
R_MOVE_TO, -2, 2,
R_LINE_TO, 0, 0

View file

@ -0,0 +1,45 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 32,
PATH_COLOR_ARGB, 0xFF, 0x1A, 0x73, 0xE8,
MOVE_TO, 11, 16,
CUBIC_TO, 10, 17.66f, 9.66f, 19, 8, 19,
CUBIC_TO, 6.34f, 19, 5, 17.66f, 5, 16,
CUBIC_TO, 5, 14.34f, 6.34f, 13, 8, 13,
CUBIC_TO, 9.66f, 13, 11, 14.34f, 11, 16,
CLOSE,
MOVE_TO, 19, 16,
CUBIC_TO, 19, 17.66f, 17.66f, 19, 16, 19,
CUBIC_TO, 14.34f, 19, 13, 17.66f, 13, 16,
CUBIC_TO, 13, 14.34f, 14.34f, 13, 16, 13,
CUBIC_TO, 17.66f, 13, 19, 14.34f, 19, 16,
CLOSE,
MOVE_TO, 27, 16,
CUBIC_TO, 27, 17.66f, 25.66f, 19, 24, 19,
CUBIC_TO, 22.34f, 19, 21, 17.66f, 21, 16,
CUBIC_TO, 21, 14.34f, 22.34f, 13, 24, 13,
CUBIC_TO, 25.66f, 13, 27, 14.34f, 27, 16,
CLOSE
CANVAS_DIMENSIONS, 16,
PATH_COLOR_ARGB, 0xFF, 0x1A, 0x73, 0xE8,
MOVE_TO, 3, 6.5f,
CUBIC_TO, 2.17f, 6.5f, 1.5f, 7.17f, 1.5f, 8,
CUBIC_TO, 1.5f, 8.83f, 2.17f, 9.5f, 3, 9.5f,
CUBIC_TO, 3.83f, 9.5f, 4.5f, 8.83f, 4.5f, 8,
CUBIC_TO, 4.5f, 7.17f, 3.83f, 6.5, 3, 6.5f,
CLOSE,
MOVE_TO, 8, 6.5f,
CUBIC_TO, 7.17f, 6.5f, 6.5f, 7.17f, 6.5f, 8,
CUBIC_TO, 6.5f, 8.83f, 7.17f, 9.5f, 8, 9.5f,
CUBIC_TO, 8.83f, 9.5f, 9.5f, 8.83f, 9.5f, 8,
CUBIC_TO, 9.5f, 7.17f, 8.83f, 6.5f, 8, 6.5f,
CLOSE,
MOVE_TO, 13, 6.5f,
CUBIC_TO, 12.17f, 6.5f, 11.5f, 7.17f, 11.5f, 8,
CUBIC_TO, 11.5f, 8.83f, 12.17f, 9.5f, 13, 9.5f,
CUBIC_TO, 13.83f, 9.5f, 14.5f, 8.83f, 14.5f, 8,
CUBIC_TO, 14.5f, 7.17f, 13.83f, 6.5f, 13, 6.5f,
CLOSE

View file

@ -0,0 +1,127 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// Size 25 is added for better appearance at 125% scale.
CANVAS_DIMENSIONS, 25,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
CIRCLE, 12.5, 12.5, 12.5,
MOVE_TO, 16.41f, 13.37f,
R_ARC_TO, 3.04f, 3.04f, 0, 0, 1, 3.04f, 3.04f,
R_ARC_TO, 3.04f, 3.04f, 0, 0, 1, -3.04f, 3.04f,
R_CUBIC_TO, -1.59f, 0, -2.87f, -1.22f, -3.01f, -2.78f,
R_CUBIC_TO, -0.84f, -0.54f, -1.53f, -0.2f, -1.79f, -0.02f,
R_ARC_TO, 3.02f, 3.02f, 0, 0, 1, -3.01f, 2.8f,
R_ARC_TO, 3.04f, 3.04f, 0, 0, 1, -3.04f, -3.04f,
R_ARC_TO, 3.04f, 3.04f, 0, 0, 1, 3.04f, -3.04f,
R_ARC_TO, 3.04f, 3.04f, 0, 0, 1, 2.95f, 2.34f,
R_ARC_TO, 2.38f, 2.38f, 0, 0, 1, 1.91f, 0.01f,
R_ARC_TO, 3.03f, 3.03f, 0, 0, 1, 2.95f, -2.35f,
CLOSE,
R_MOVE_TO, -7.81f, 0.87f,
R_ARC_TO, 2.17f, 2.17f, 0, 1, 0, 0, 4.34f,
R_ARC_TO, 2.17f, 2.17f, 0, 0, 0, 0, -4.34f,
CLOSE,
R_MOVE_TO, 7.81f, 0,
R_ARC_TO, 2.17f, 2.17f, 0, 1, 0, 0, 4.34f,
R_ARC_TO, 2.17f, 2.17f, 0, 0, 0, 0, -4.34f,
CLOSE,
MOVE_TO, 20.31f, 11,
R_V_LINE_TO, 1,
H_LINE_TO, 4.69f,
R_V_LINE_TO, -1,
R_H_LINE_TO, 15.63f,
CLOSE,
R_MOVE_TO, -4.97f, -5.64f,
R_LINE_TO, 0.05f, 0.11f,
LINE_TO, 17.05f, 10,
H_LINE_TO, 7.95f,
R_LINE_TO, 1.65f, -4.53f,
R_ARC_TO, 0.87f, 0.87f, 0, 0, 1, 0.96f, -0.55f,
R_LINE_TO, 0.12f, 0.03f,
R_LINE_TO, 1.81f, 0.61f,
R_LINE_TO, 1.81f, -0.61f,
R_ARC_TO, 0.87f, 0.87f, 0, 0, 1, 1.03f, 0.41f,
CLOSE
CANVAS_DIMENSIONS, 24,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
CIRCLE, 12, 12, 12,
MOVE_TO, 15.75f, 12.83f,
R_ARC_TO, 2.92f, 2.92f, 0, 0, 1, 2.92f, 2.92f,
R_ARC_TO, 2.92f, 2.92f, 0, 0, 1, -2.92f, 2.92f,
R_CUBIC_TO, -1.52f, 0, -2.76f, -1.17f, -2.89f, -2.67f,
R_CUBIC_TO, -0.81f, -0.52f, -1.47f, -0.19f, -1.72f, -0.02f,
R_ARC_TO, 2.9f, 2.9f, 0, 0, 1, -2.89f, 2.68f,
R_ARC_TO, 2.92f, 2.92f, 0, 0, 1, -2.92f, -2.92f,
R_ARC_TO, 2.92f, 2.92f, 0, 0, 1, 2.92f, -2.92f,
R_ARC_TO, 2.92f, 2.92f, 0, 0, 1, 2.83f, 2.25f,
R_ARC_TO, 2.29f, 2.29f, 0, 0, 1, 1.83f, 0.01f,
R_ARC_TO, 2.91f, 2.91f, 0, 0, 1, 2.83f, -2.26f,
CLOSE,
R_MOVE_TO, -7.5f, 0.83f,
R_ARC_TO, 2.08f, 2.08f, 0, 1, 0, 0, 4.17f,
R_ARC_TO, 2.08f, 2.08f, 0, 0, 0, 0, -4.17f,
CLOSE,
R_MOVE_TO, 7.5f, 0,
R_ARC_TO, 2.08f, 2.08f, 0, 1, 0, 0, 4.17f,
R_ARC_TO, 2.08f, 2.08f, 0, 0, 0, 0, -4.17f,
CLOSE,
MOVE_TO, 19.5f, 11,
R_V_LINE_TO, 1,
R_H_LINE_TO, -15,
R_V_LINE_TO, -1,
R_H_LINE_TO, 15,
CLOSE,
R_MOVE_TO, -4.77f, -5.85f,
R_LINE_TO, 0.05f, 0.1f,
R_LINE_TO, 1.6f, 4.25f,
R_LINE_TO, -8.74f, -0.01f,
LINE_TO, 9.22f, 5.25f,
R_ARC_TO, 0.84f, 0.84f, 0, 0, 1, 0.94f, -0.53f,
R_LINE_TO, 0.11f, 0.03f,
LINE_TO, 12, 5.33f,
R_LINE_TO, 1.73f, -0.58f,
R_CUBIC_TO, 0.39f, -0.13f, 0.81f, 0.05f, 1, 0.4f,
CLOSE
CANVAS_DIMENSIONS, 20,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
CIRCLE, 10, 10, 10,
MOVE_TO, 13.13f, 10.69f,
R_CUBIC_TO, 1.34f, 0, 2.43f, 1.09f, 2.43f, 2.43f,
R_CUBIC_TO, 0, 1.34f, -1.09f, 2.43f, -2.43f, 2.43f,
R_CUBIC_TO, -1.27f, 0, -2.3f, -0.98f, -2.41f, -2.22f,
R_CUBIC_TO, -0.67f, -0.43f, -1.22f, -0.16f, -1.43f, -0.01f,
R_ARC_TO, 2.42f, 2.42f, 0, 0, 1, -2.41f, 2.24f,
R_CUBIC_TO, -1.34f, 0, -2.43f, -1.09f, -2.43f, -2.43f,
R_CUBIC_TO, 0, -1.34f, 1.09f, -2.43f, 2.43f, -2.43f,
R_CUBIC_TO, 1.15f, 0, 2.1f, 0.8f, 2.36f, 1.87f,
R_ARC_TO, 1.91f, 1.91f, 0, 0, 1, 1.53f, 0.01f,
R_ARC_TO, 2.43f, 2.43f, 0, 0, 1, 2.36f, -1.88f,
CLOSE,
R_MOVE_TO, -6.25f, 0.7f,
R_ARC_TO, 1.74f, 1.74f, 0, 1, 0, 0, 3.47f,
R_ARC_TO, 1.74f, 1.74f, 0, 0, 0, 0, -3.47f,
CLOSE,
R_MOVE_TO, 6.25f, 0,
R_ARC_TO, 1.74f, 1.74f, 0, 1, 0, 0, 3.47f,
R_ARC_TO, 1.74f, 1.74f, 0, 0, 0, 0, -3.47f,
CLOSE,
MOVE_TO, 16.25f, 9,
R_V_LINE_TO, 1,
H_LINE_TO, 3.75f,
V_LINE_TO, 9,
R_H_LINE_TO, 12.5f,
CLOSE,
R_MOVE_TO, -3.98f, -4.72f,
R_LINE_TO, 0.04f, 0.09f,
LINE_TO, 13.64f, 8,
H_LINE_TO, 6.36f,
LINE_TO, 7.68f, 4.38f,
R_CUBIC_TO, 0.12f, -0.32f, 0.45f, -0.5f, 0.77f, -0.44f,
R_LINE_TO, 0.1f, 0.02f,
LINE_TO, 10, 4.44f,
R_LINE_TO, 1.44f, -0.49f,
R_ARC_TO, 0.7f, 0.7f, 0, 0, 1, 0.83f, 0.33f,
CLOSE

View file

@ -0,0 +1,115 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
CANVAS_DIMENSIONS, 288,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
MOVE_TO, 217, -1,
H_LINE_TO, 288,
V_LINE_TO, 80,
H_LINE_TO, 274.16f,
LINE_TO, 272.69f, 67.98f,
CUBIC_TO, 270.89f, 68.5f, 268.99f, 68.82f, 266.99f, 68.82f,
CUBIC_TO, 256.97f, 68.82f, 248.85f, 61.12f, 247.9f, 51.2f,
CUBIC_TO, 242.52f, 47.83f, 238.19f, 49.94f, 236.61f, 51.1f,
CUBIC_TO, 235.87f, 61.01f, 227.65f, 68.82f, 217.52f, 68.82f,
CUBIC_TO, 206.87f, 68.82f, 198.32f, 60.17f, 198.32f, 49.62f,
CUBIC_TO, 198.32f, 38.97f, 206.97f, 30.42f, 217.52f, 30.42f,
CUBIC_TO, 226.59f, 30.42f, 234.19f, 36.75f, 236.19f, 45.3f,
CUBIC_TO, 239.35f, 43.93f, 243.68f, 43.4f, 248.32f, 45.4f,
CUBIC_TO, 250.32f, 36.86f, 257.92f, 30.53f, 266.99f, 30.53f,
H_LINE_TO, 268.26f,
LINE_TO, 267.62f, 24.94f,
H_LINE_TO, 192.73f,
H_LINE_TO, 100.12f,
LINE_TO, 106.13f, 17.24f,
H_LINE_TO, 182.08f,
LINE_TO, 175.2f, -1,
H_LINE_TO, 200.5f,
LINE_TO, 194.63f, 19.35f,
H_LINE_TO, 266.99f,
LINE_TO, 266.36f, 13.86f,
H_LINE_TO, 211.3f,
LINE_TO, 217, -1,
CLOSE,
MOVE_TO, 70.9f, -1,
H_LINE_TO, 0,
V_LINE_TO, 80,
H_LINE_TO, 81.13f,
CUBIC_TO, 79.02f, 76.1f, 77.76f, 71.67f, 77.76f, 66.92f,
CUBIC_TO, 77.76f, 52.15f, 89.78f, 40.13f, 104.55f, 40.13f,
CUBIC_TO, 117.21f, 40.13f, 127.76f, 48.99f, 130.6f, 60.8f,
CUBIC_TO, 135.03f, 58.9f, 141.05f, 58.17f, 147.48f, 60.91f,
CUBIC_TO, 150.22f, 48.99f, 160.88f, 40.13f, 173.53f, 40.13f,
CUBIC_TO, 178.6f, 40.13f, 183.34f, 41.61f, 187.35f, 44.03f,
LINE_TO, 190.73f, 32.53f,
H_LINE_TO, 94.11f,
LINE_TO, 85.04f, 43.93f,
CUBIC_TO, 85.56f, 42.34f, 85.78f, 40.76f, 85.78f, 39.07f,
CUBIC_TO, 85.78f, 29.69f, 78.08f, 21.99f, 68.69f, 21.99f,
CUBIC_TO, 60.57f, 21.99f, 53.82f, 27.68f, 52.02f, 35.17f,
CUBIC_TO, 47.91f, 33.48f, 44.11f, 33.91f, 41.26f, 35.17f,
CUBIC_TO, 39.58f, 28.32f, 33.88f, 23.04f, 26.81f, 22.09f,
LINE_TO, 28.71f, 17.03f,
H_LINE_TO, 90.73f,
V_LINE_TO, 12.18f,
H_LINE_TO, 30.5f,
LINE_TO, 32.3f, 7.32f,
H_LINE_TO, 74.07f,
LINE_TO, 70.9f, -1,
CLOSE,
MOVE_TO, 90.52f, 80,
H_LINE_TO, 118.37f,
CUBIC_TO, 121.53f, 76.52f, 123.54f, 71.98f, 123.54f, 66.92f,
CUBIC_TO, 123.54f, 56.37f, 114.99f, 47.83f, 104.45f, 47.83f,
CUBIC_TO, 93.9f, 47.83f, 85.35f, 56.37f, 85.35f, 66.92f,
CUBIC_TO, 85.35f, 71.98f, 87.36f, 76.62f, 90.52f, 80,
CLOSE,
MOVE_TO, 127.65f, 80,
H_LINE_TO, 149.91f,
CUBIC_TO, 148.11f, 76.73f, 146.95f, 73.14f, 146.64f, 69.24f,
CUBIC_TO, 139.25f, 64.49f, 133.24f, 67.55f, 130.92f, 69.14f,
CUBIC_TO, 130.6f, 73.04f, 129.44f, 76.73f, 127.65f, 80,
CLOSE,
MOVE_TO, 159.19f, 80,
H_LINE_TO, 176.91f,
LINE_TO, 184.72f, 51.73f,
CUBIC_TO, 181.45f, 49.31f, 177.44f, 47.83f, 173.11f, 47.83f,
CUBIC_TO, 162.56f, 47.83f, 154.02f, 56.37f, 154.02f, 66.92f,
CUBIC_TO, 154.02f, 71.98f, 156.03f, 76.62f, 159.19f, 80,
CLOSE,
MOVE_TO, 80.92f, 39.07f,
CUBIC_TO, 80.92f, 45.83f, 75.45f, 51.31f, 68.69f, 51.31f,
CUBIC_TO, 61.93f, 51.31f, 56.45f, 45.83f, 56.45f, 39.07f,
CUBIC_TO, 56.45f, 32.32f, 61.93f, 26.84f, 68.69f, 26.84f,
CUBIC_TO, 75.45f, 26.84f, 80.92f, 32.32f, 80.92f, 39.07f,
CLOSE,
MOVE_TO, 51.71f, 40.55f,
CUBIC_TO, 46.96f, 37.49f, 43.06f, 39.39f, 41.58f, 40.45f,
CUBIC_TO, 40.95f, 49.2f, 33.56f, 56.16f, 24.6f, 56.16f,
CUBIC_TO, 21.12f, 56.16f, 17.85f, 55.11f, 15.1f, 53.31f,
LINE_TO, 5.29f, 80,
H_LINE_TO, 56.45f,
LINE_TO, 77.13f, 53.95f,
CUBIC_TO, 74.59f, 55.42f, 71.75f, 56.16f, 68.69f, 56.16f,
CUBIC_TO, 59.72f, 56.16f, 52.44f, 49.31f, 51.71f, 40.55f,
CLOSE,
MOVE_TO, 36.83f, 39.07f,
CUBIC_TO, 36.83f, 32.43f, 31.56f, 27.05f, 25.02f, 26.84f,
LINE_TO, 16.9f, 48.57f,
CUBIC_TO, 19.01f, 50.25f, 21.64f, 51.31f, 24.6f, 51.31f,
CUBIC_TO, 31.35f, 51.31f, 36.83f, 45.82f, 36.83f, 39.07f,
CLOSE,
MOVE_TO, 231.23f, 49.62f,
CUBIC_TO, 231.23f, 57.2f, 225.09f, 63.33f, 217.52f, 63.33f,
CUBIC_TO, 209.95f, 63.33f, 203.81f, 57.2f, 203.81f, 49.62f,
CUBIC_TO, 203.81f, 42.05f, 209.95f, 35.91f, 217.52f, 35.91f,
CUBIC_TO, 225.09f, 35.91f, 231.23f, 42.05f, 231.23f, 49.62f,
CLOSE,
MOVE_TO, 253.28f, 49.62f,
CUBIC_TO, 253.28f, 57.22f, 259.39f, 63.33f, 266.99f, 63.33f,
CUBIC_TO, 268.78f, 63.33f, 270.47f, 63.02f, 272.05f, 62.39f,
LINE_TO, 268.89f, 36.02f,
CUBIC_TO, 268.26f, 35.91f, 267.62f, 35.91f, 266.88f, 35.91f,
CUBIC_TO, 259.39f, 35.8f, 253.28f, 42.03f, 253.28f, 49.62f,
CLOSE

View file

@ -0,0 +1,49 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// This icon has a bigger circle to figure ratio in compare to incognito.icon.
CANVAS_DIMENSIONS, 40,
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
CIRCLE, 20, 20, 20,
MOVE_TO, 25.5f, 21.64f,
CUBIC_TO, 27.86f, 21.64f, 29.78f, 23.52f, 29.78f, 25.82f,
CUBIC_TO, 29.78f, 28.13f, 27.86f, 30, 25.5f, 30,
CUBIC_TO, 23.26f, 30, 21.45f, 28.32f, 21.26f, 26.18f,
CUBIC_TO, 20.07f, 25.44f, 19.11f, 25.9f, 18.74f, 26.16f,
CUBIC_TO, 18.57f, 28.3f, 16.75f, 30, 14.5f, 30,
CUBIC_TO, 12.14f, 30, 10.22f, 28.13f, 10.22f, 25.82f,
CUBIC_TO, 10.22f, 23.52f, 12.14f, 21.64f, 14.5f, 21.64f,
CUBIC_TO, 16.52f, 21.64f, 18.2f, 23.02f, 18.66f, 24.87f,
CUBIC_TO, 19.36f, 24.57f, 20.32f, 24.45f, 21.34f, 24.88f,
CUBIC_TO, 21.78f, 23.03f, 23.47f, 21.64f, 25.5f, 21.64f,
CLOSE,
MOVE_TO, 14.5f, 22.84f,
CUBIC_TO, 12.81f, 22.84f, 11.44f, 24.17f, 11.44f, 25.82f,
CUBIC_TO, 11.44f, 27.47f, 12.81f, 28.81f, 14.5f, 28.81f,
CUBIC_TO, 16.19f, 28.81f, 17.56f, 27.47f, 17.56f, 25.82f,
CUBIC_TO, 17.56f, 24.17f, 16.19f, 22.84f, 14.5f, 22.84f,
CLOSE,
MOVE_TO, 25.5f, 22.84f,
CUBIC_TO, 23.81f, 22.84f, 22.44f, 24.17f, 22.44f, 25.82f,
CUBIC_TO, 22.44f, 27.47f, 23.81f, 28.81f, 25.5f, 28.81f,
CUBIC_TO, 27.19f, 28.81f, 28.56f, 27.47f, 28.56f, 25.82f,
CUBIC_TO, 28.56f, 24.17f, 27.19f, 22.84f, 25.5f, 22.84f,
CLOSE,
MOVE_TO, 31, 19.02f,
LINE_TO, 31, 20.5f,
LINE_TO, 9, 20.5f,
LINE_TO, 9, 19.02f,
LINE_TO, 31, 19.02f,
CLOSE,
MOVE_TO, 24.02f, 10.66f,
LINE_TO, 24.07f, 10.78f,
LINE_TO, 26.5f, 17,
LINE_TO, 13.5f, 17,
LINE_TO, 15.92f, 10.78f,
CUBIC_TO, 16.13f, 10.22f, 16.73f, 9.9f, 17.32f, 10.03f,
LINE_TO, 17.45f, 10.06f,
LINE_TO, 20, 10.9f,
LINE_TO, 22.54f, 10.06f,
CUBIC_TO, 23.12f, 9.87f, 23.75f, 10.14f, 24.02f, 10.66f,
CLOSE

View file

@ -0,0 +1,48 @@
// Copyright 2015 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.
PATH_COLOR_ARGB, 0xFF, 0xE5, 0x1C, 0x23,
MOVE_TO, 38, 13,
LINE_TO, 21, 13,
LINE_TO, 17, 7,
LINE_TO, 10, 7,
CUBIC_TO, 7.7f, 7, 6.02f, 8.69f, 6, 11,
LINE_TO, 6, 37,
CUBIC_TO, 6, 39.31f, 7.7f, 41, 10, 41,
LINE_TO, 38, 41,
CUBIC_TO, 40.3f, 41, 42, 39.31f, 42, 37,
LINE_TO, 42, 17,
CUBIC_TO, 42, 14.36f, 40.3f, 12.67f, 38, 13,
LINE_TO, 38, 13,
LINE_TO, 38, 13,
CLOSE,
MOVE_TO, 16, 18,
LINE_TO, 20, 18,
LINE_TO, 20, 23,
LINE_TO, 16, 23,
LINE_TO, 16, 18,
LINE_TO, 16, 18,
CLOSE,
MOVE_TO, 33, 35,
LINE_TO, 29, 35,
LINE_TO, 29, 31,
LINE_TO, 20, 31,
LINE_TO, 20, 35,
LINE_TO, 16, 35,
LINE_TO, 16, 31,
LINE_TO, 20, 31,
LINE_TO, 20, 27,
LINE_TO, 29, 27,
LINE_TO, 29, 31,
LINE_TO, 33, 31,
LINE_TO, 33, 35,
LINE_TO, 33, 35,
CLOSE,
MOVE_TO, 28, 18,
LINE_TO, 32, 18,
LINE_TO, 32, 23,
LINE_TO, 28, 23,
LINE_TO, 28, 18,
LINE_TO, 28, 18,
CLOSE

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,149 @@
// Copyright (c) 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/memory_details.h"
#include <stddef.h>
#include <sys/types.h>
#include <unistd.h>
#include <map>
#include <memory>
#include <set>
#include "base/bind.h"
#include "base/files/file_util.h"
#include "base/process/process_iterator.h"
#include "base/process/process_metrics.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/string_util.h"
#include "base/strings/utf_string_conversions.h"
#include "base/threading/scoped_blocking_call.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/common/chrome_constants.h"
#include "chrome/grit/chromium_strings.h"
#include "content/public/browser/browser_task_traits.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/common/process_type.h"
#include "ui/base/l10n/l10n_util.h"
using base::ProcessEntry;
namespace {
struct Process {
pid_t pid;
pid_t parent;
};
typedef std::map<pid_t, Process> ProcessMap;
// Get information on all the processes running on the system.
ProcessMap GetProcesses() {
ProcessMap map;
base::ProcessIterator process_iter(NULL);
while (const ProcessEntry* process_entry = process_iter.NextProcessEntry()) {
Process process;
process.pid = process_entry->pid();
process.parent = process_entry->parent_pid();
map.insert(std::make_pair(process.pid, process));
}
return map;
}
// For each of a list of pids, collect memory information about that process.
ProcessData GetProcessDataMemoryInformation(
const std::vector<pid_t>& pids) {
ProcessData process_data;
for (pid_t pid : pids) {
ProcessMemoryInformation pmi;
pmi.pid = pid;
pmi.num_processes = 1;
if (pmi.pid == base::GetCurrentProcId())
pmi.process_type = content::PROCESS_TYPE_BROWSER;
else
pmi.process_type = content::PROCESS_TYPE_UNKNOWN;
std::unique_ptr<base::ProcessMetrics> metrics(
base::ProcessMetrics::CreateProcessMetrics(pid));
pmi.num_open_fds = metrics->GetOpenFdCount();
pmi.open_fds_soft_limit = metrics->GetOpenFdSoftLimit();
process_data.processes.push_back(pmi);
}
return process_data;
}
// Find all children of the given process with pid |root|.
std::vector<pid_t> GetAllChildren(const ProcessMap& processes, pid_t root) {
std::vector<pid_t> children;
children.push_back(root);
std::set<pid_t> wavefront, next_wavefront;
wavefront.insert(root);
while (wavefront.size()) {
for (const auto& entry : processes) {
const Process& process = entry.second;
if (wavefront.count(process.parent)) {
children.push_back(process.pid);
next_wavefront.insert(process.pid);
}
}
wavefront.clear();
wavefront.swap(next_wavefront);
}
return children;
}
} // namespace
MemoryDetails::MemoryDetails() {
}
ProcessData* MemoryDetails::ChromeBrowser() {
return &process_data_[0];
}
void MemoryDetails::CollectProcessData(
const std::vector<ProcessMemoryInformation>& child_info) {
base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
base::BlockingType::MAY_BLOCK);
ProcessMap process_map = GetProcesses();
std::set<pid_t> browsers_found;
ProcessData current_browser =
GetProcessDataMemoryInformation(GetAllChildren(process_map, getpid()));
current_browser.name = l10n_util::GetStringUTF16(IDS_SHORT_PRODUCT_NAME);
current_browser.process_name = u"thorium";
for (auto i = current_browser.processes.begin();
i != current_browser.processes.end(); ++i) {
// Check if this is one of the child processes whose data we collected
// on the IO thread, and if so copy over that data.
for (size_t child = 0; child < child_info.size(); child++) {
if (child_info[child].pid != i->pid)
continue;
i->titles = child_info[child].titles;
i->process_type = child_info[child].process_type;
break;
}
}
process_data_.push_back(current_browser);
#if BUILDFLAG(IS_CHROMEOS_ASH)
base::GetSwapInfo(&swap_info_);
#endif
// Finally return to the browser thread.
content::GetUIThreadTaskRunner({})->PostTask(
FROM_HERE,
base::BindOnce(&MemoryDetails::CollectChildInfoOnUIThread, this));
}

View file

@ -0,0 +1,386 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/net/stub_resolver_config_reader.h"
#include <set>
#include <string>
#include <utility>
#include <vector>
#include "base/bind.h"
#include "base/callback.h"
#include "base/check.h"
#include "base/feature_list.h"
#include "base/location.h"
#include "base/metrics/field_trial_params.h"
#include "base/metrics/histogram_macros.h"
#include "base/notreached.h"
#include "base/strings/string_piece.h"
#include "base/values.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/net/secure_dns_config.h"
#include "chrome/browser/net/secure_dns_util.h"
#include "chrome/browser/policy/chrome_browser_policy_connector.h"
#include "chrome/common/chrome_features.h"
#include "chrome/common/pref_names.h"
#include "components/flags_ui/pref_service_flags_storage.h"
#include "components/prefs/pref_registry_simple.h"
#include "components/prefs/pref_service.h"
#include "content/public/browser/network_service_instance.h"
#include "net/dns/public/dns_over_https_config.h"
#include "net/dns/public/secure_dns_mode.h"
#include "net/dns/public/util.h"
#include "services/network/public/mojom/host_resolver.mojom.h"
#include "services/network/public/mojom/network_service.mojom.h"
#if BUILDFLAG(IS_ANDROID)
#include "base/android/build_info.h"
#include "chrome/browser/enterprise/util/android_enterprise_info.h"
#endif
#if BUILDFLAG(IS_WIN)
#include "base/enterprise_util.h"
#include "base/win/win_util.h"
#include "base/win/windows_version.h"
#include "chrome/browser/win/parental_controls.h"
#endif
namespace {
// Detailed descriptions of the secure DNS mode. These values are logged to UMA.
// Entries should not be renumbered and numeric values should never be reused.
// Please keep in sync with "SecureDnsModeDetails" in
// src/tools/metrics/histograms/enums.xml.
enum class SecureDnsModeDetailsForHistogram {
// The mode is controlled by the user and is set to 'off'.
kOffByUser = 0,
// The mode is controlled via enterprise policy and is set to 'off'.
kOffByEnterprisePolicy = 1,
// Chrome detected a managed environment and forced the mode to 'off'.
kOffByDetectedManagedEnvironment = 2,
// Chrome detected parental controls and forced the mode to 'off'.
kOffByDetectedParentalControls = 3,
// The mode is controlled by the user and is set to 'automatic' (the default
// mode).
kAutomaticByUser = 4,
// The mode is controlled via enterprise policy and is set to 'automatic'.
kAutomaticByEnterprisePolicy = 5,
// The mode is controlled by the user and is set to 'secure'.
kSecureByUser = 6,
// The mode is controlled via enterprise policy and is set to 'secure'.
kSecureByEnterprisePolicy = 7,
kMaxValue = kSecureByEnterprisePolicy,
};
#if BUILDFLAG(IS_WIN)
bool ShouldDisableDohForWindowsParentalControls() {
const WinParentalControls& parental_controls = GetWinParentalControls();
if (parental_controls.web_filter)
return true;
// Some versions before Windows 8 may not fully support |web_filter|, so
// conservatively disable doh for any recognized parental controls.
if (parental_controls.any_restrictions &&
base::win::GetVersion() < base::win::Version::WIN8) {
return true;
}
return false;
}
#endif // BUILDFLAG(IS_WIN)
// Check the AsyncDns field trial and return true if it should be enabled. On
// Android this includes checking the Android version in the field trial.
bool ShouldEnableAsyncDns() {
bool feature_can_be_enabled = true;
#if BUILDFLAG(IS_ANDROID)
int min_sdk =
base::GetFieldTrialParamByFeatureAsInt(features::kAsyncDns, "min_sdk", 0);
if (base::android::BuildInfo::GetInstance()->sdk_int() < min_sdk)
feature_can_be_enabled = false;
#endif
return feature_can_be_enabled &&
base::FeatureList::IsEnabled(features::kAsyncDns);
}
} // namespace
// static
constexpr base::TimeDelta StubResolverConfigReader::kParentalControlsCheckDelay;
StubResolverConfigReader::StubResolverConfigReader(PrefService* local_state,
bool set_up_pref_defaults)
: local_state_(local_state) {
base::RepeatingClosure pref_callback =
base::BindRepeating(&StubResolverConfigReader::UpdateNetworkService,
base::Unretained(this), false /* record_metrics */);
pref_change_registrar_.Init(local_state_);
// Update the DnsClient and DoH default preferences based on the corresponding
// features before registering change callbacks for these preferences.
// Changing prefs or defaults after registering change callbacks could result
// in reentrancy and mess up registration between this code and NetworkService
// creation.
if (set_up_pref_defaults) {
local_state_->SetDefaultPrefValue(prefs::kBuiltInDnsClientEnabled,
base::Value(ShouldEnableAsyncDns()));
net::SecureDnsMode default_secure_dns_mode = net::SecureDnsMode::kOff;
std::string default_doh_templates;
if (base::FeatureList::IsEnabled(features::kDnsOverHttps)) {
if (features::kDnsOverHttpsFallbackParam.Get()) {
default_secure_dns_mode = net::SecureDnsMode::kAutomatic;
} else {
default_secure_dns_mode = net::SecureDnsMode::kSecure;
}
default_doh_templates = features::kDnsOverHttpsTemplatesParam.Get();
}
local_state_->SetDefaultPrefValue(
prefs::kDnsOverHttpsMode,
base::Value(SecureDnsConfig::ModeToString(default_secure_dns_mode)));
local_state_->SetDefaultPrefValue(prefs::kDnsOverHttpsTemplates,
base::Value(default_doh_templates));
// If the user has explicitly enabled or disabled the DoH experiment in
// chrome://flags and the DoH UI setting is not visible, store that choice
// in the user prefs so that it can be persisted after the experiment ends.
// Also make sure to remove the stored prefs value if the user has changed
// their chrome://flags selection to the default.
if (!features::kDnsOverHttpsShowUiParam.Get()) {
flags_ui::PrefServiceFlagsStorage flags_storage(local_state_);
std::set<std::string> entries = flags_storage.GetFlags();
if (entries.count("dns-over-https@1")) {
// The user has "Enabled" selected.
local_state_->SetString(prefs::kDnsOverHttpsMode,
SecureDnsConfig::kModeSecure);
} else if (entries.count("dns-over-https@2")) {
// The user has "Disabled" selected.
local_state_->SetString(prefs::kDnsOverHttpsMode,
SecureDnsConfig::kModeOff);
} else {
// The user has "Default" selected.
local_state_->ClearPref(prefs::kDnsOverHttpsMode);
}
}
}
pref_change_registrar_.Add(prefs::kBuiltInDnsClientEnabled, pref_callback);
pref_change_registrar_.Add(prefs::kDnsOverHttpsMode, pref_callback);
pref_change_registrar_.Add(prefs::kDnsOverHttpsTemplates, pref_callback);
pref_change_registrar_.Add(prefs::kAdditionalDnsQueryTypesEnabled,
pref_callback);
parental_controls_delay_timer_.Start(
FROM_HERE, kParentalControlsCheckDelay,
base::BindOnce(&StubResolverConfigReader::OnParentalControlsDelayTimer,
base::Unretained(this)));
#if BUILDFLAG(IS_ANDROID)
chrome::enterprise_util::AndroidEnterpriseInfo::GetInstance()
->GetAndroidEnterpriseInfoState(base::BindOnce(
&StubResolverConfigReader::OnAndroidOwnedStateCheckComplete,
weak_factory_.GetWeakPtr()));
#endif
}
StubResolverConfigReader::~StubResolverConfigReader() = default;
// static
void StubResolverConfigReader::RegisterPrefs(PrefRegistrySimple* registry) {
// Register the DnsClient and DoH preferences. The feature list has not been
// initialized yet, so setting the preference defaults here to reflect the
// corresponding features will only cause the preference defaults to reflect
// the feature defaults (feature values set via the command line will not be
// captured). Thus, the preference defaults are updated in the constructor
// for SystemNetworkContextManager, at which point the feature list is ready.
registry->RegisterBooleanPref(prefs::kBuiltInDnsClientEnabled, false);
registry->RegisterStringPref(prefs::kDnsOverHttpsMode, std::string());
registry->RegisterStringPref(prefs::kDnsOverHttpsTemplates, std::string());
registry->RegisterBooleanPref(prefs::kAdditionalDnsQueryTypesEnabled, true);
}
SecureDnsConfig StubResolverConfigReader::GetSecureDnsConfiguration(
bool force_check_parental_controls_for_automatic_mode) {
return GetAndUpdateConfiguration(
force_check_parental_controls_for_automatic_mode,
false /* record_metrics */, false /* update_network_service */);
}
void StubResolverConfigReader::UpdateNetworkService(bool record_metrics) {
GetAndUpdateConfiguration(
false /* force_check_parental_controls_for_automatic_mode */,
record_metrics, true /* update_network_service */);
}
bool StubResolverConfigReader::ShouldDisableDohForManaged() {
// This function ignores cloud policies which are loaded on a per-profile basis.
#if BUILDFLAG(IS_ANDROID)
// Check for MDM/management/owner apps. android_has_owner_ is true if either a
// device or policy owner app is discovered by
// GetAndroidEnterpriseInfoState(). If android_has_owner_ is nullopt, take a
// value of false so that we don't disable DoH during the async check.
// Because Android policies can only be loaded with owner apps this is
// sufficient to check for the prescences of policies as well.
if (android_has_owner_.value_or(false))
return true;
#elif BUILDFLAG(IS_WIN)
// TODO(crbug.com/1339062): What is the correct function to use here? (This
// may or may not obsolete the following TODO)
// TODO (crbug.com/1320766): For legacy compatibility, this uses
// IsEnterpriseDevice() which effectively equates to a domain join check.
// Consider whether this should use IsManagedDevice() instead.
if (base::win::IsEnrolledToDomain())
return true;
#endif
#if !BUILDFLAG(IS_ANDROID) && !BUILDFLAG(IS_CHROMEOS)
if (g_browser_process->browser_policy_connector()->HasMachineLevelPolicies())
return true;
#endif
return false;
}
bool StubResolverConfigReader::ShouldDisableDohForParentalControls() {
if (parental_controls_testing_override_.has_value())
return parental_controls_testing_override_.value();
#if BUILDFLAG(IS_WIN)
return ShouldDisableDohForWindowsParentalControls();
#else
return false;
#endif
}
void StubResolverConfigReader::OnParentalControlsDelayTimer() {
DCHECK(!parental_controls_delay_timer_.IsRunning());
// No need to act if parental controls were checked early.
if (parental_controls_checked_)
return;
parental_controls_checked_ = true;
// If parental controls are enabled, force a config change so secure DNS can
// be disabled.
if (ShouldDisableDohForParentalControls())
UpdateNetworkService(false /* record_metrics */);
}
bool StubResolverConfigReader::GetInsecureStubResolverEnabled() {
return local_state_->GetBoolean(prefs::kBuiltInDnsClientEnabled);
}
SecureDnsConfig StubResolverConfigReader::GetAndUpdateConfiguration(
bool force_check_parental_controls_for_automatic_mode,
bool record_metrics,
bool update_network_service) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
net::SecureDnsMode secure_dns_mode;
SecureDnsModeDetailsForHistogram mode_details;
SecureDnsConfig::ManagementMode forced_management_mode =
SecureDnsConfig::ManagementMode::kNoOverride;
bool is_managed =
local_state_->FindPreference(prefs::kDnsOverHttpsMode)->IsManaged();
if (!is_managed && ShouldDisableDohForManaged()) {
secure_dns_mode = net::SecureDnsMode::kOff;
forced_management_mode = SecureDnsConfig::ManagementMode::kDisabledManaged;
} else {
secure_dns_mode = SecureDnsConfig::ParseMode(
local_state_->GetString(prefs::kDnsOverHttpsMode))
.value_or(net::SecureDnsMode::kOff);
}
bool check_parental_controls = false;
if (secure_dns_mode == net::SecureDnsMode::kSecure) {
mode_details =
is_managed ? SecureDnsModeDetailsForHistogram::kSecureByEnterprisePolicy
: SecureDnsModeDetailsForHistogram::kSecureByUser;
// SECURE mode must always check for parental controls immediately (unless
// enabled through policy, which takes precedence over parental controls)
// because the mode allows sending DoH requests immediately.
check_parental_controls = !is_managed;
} else if (secure_dns_mode == net::SecureDnsMode::kAutomatic) {
mode_details =
is_managed
? SecureDnsModeDetailsForHistogram::kAutomaticByEnterprisePolicy
: SecureDnsModeDetailsForHistogram::kAutomaticByUser;
// To avoid impacting startup performance, AUTOMATIC mode should defer
// checking parental for a short period. This delay should have no practical
// effect on DoH queries because DoH enabling probes do not start until a
// longer period after startup.
bool allow_check_parental_controls =
force_check_parental_controls_for_automatic_mode ||
parental_controls_checked_;
check_parental_controls = !is_managed && allow_check_parental_controls;
} else {
switch (forced_management_mode) {
case SecureDnsConfig::ManagementMode::kNoOverride:
mode_details =
is_managed
? SecureDnsModeDetailsForHistogram::kOffByEnterprisePolicy
: SecureDnsModeDetailsForHistogram::kOffByUser;
break;
case SecureDnsConfig::ManagementMode::kDisabledManaged:
mode_details =
SecureDnsModeDetailsForHistogram::kOffByDetectedManagedEnvironment;
break;
case SecureDnsConfig::ManagementMode::kDisabledParentalControls:
NOTREACHED();
break;
default:
NOTREACHED();
}
// No need to check for parental controls if DoH is already disabled.
check_parental_controls = false;
}
// Check parental controls last because it can be expensive and should only be
// checked if necessary for the otherwise-determined mode.
if (check_parental_controls) {
parental_controls_checked_ = true;
}
bool additional_dns_query_types_enabled =
local_state_->GetBoolean(prefs::kAdditionalDnsQueryTypesEnabled);
if (record_metrics) {
UMA_HISTOGRAM_ENUMERATION("Net.DNS.DnsConfig.SecureDnsMode", mode_details);
if (!additional_dns_query_types_enabled || ShouldDisableDohForManaged()) {
UMA_HISTOGRAM_BOOLEAN("Net.DNS.DnsConfig.AdditionalDnsQueryTypesEnabled",
additional_dns_query_types_enabled);
}
}
net::DnsOverHttpsConfig doh_config;
if (secure_dns_mode != net::SecureDnsMode::kOff) {
doh_config = net::DnsOverHttpsConfig::FromStringLax(
local_state_->GetString(prefs::kDnsOverHttpsTemplates));
}
if (update_network_service) {
content::GetNetworkService()->ConfigureStubHostResolver(
GetInsecureStubResolverEnabled(), secure_dns_mode, doh_config,
additional_dns_query_types_enabled);
}
return SecureDnsConfig(secure_dns_mode, std::move(doh_config),
forced_management_mode);
}
#if BUILDFLAG(IS_ANDROID)
void StubResolverConfigReader::OnAndroidOwnedStateCheckComplete(
bool has_profile_owner,
bool has_device_owner) {
DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_);
android_has_owner_ = has_profile_owner || has_device_owner;
// update the network service if the actual result is "true" to save time.
if (android_has_owner_.value())
UpdateNetworkService(false /* record_metrics */);
}
#endif

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" width="48" height="48" fill="#FBBC04"><path d="M0 0h48v48H0z" fill="none"/><path d="M2 42h44L24 4 2 42zm24-6h-4v-4h4v4zm0-8h-4v-8h4v8z"/></svg>

After

Width:  |  Height:  |  Size: 184 B

View file

@ -0,0 +1 @@
<svg width="16" height="16" xmlns="http://www.w3.org/2000/svg"><g fill="#E51C23"><circle cx="5.44" cy="10.371" r="1.411"/><path d="M8 0C3.578 0 0 3.578 0 8c0 4.422 3.578 8 8 8 4.422 0 8-3.578 8-8 0-4.422-3.578-8-8-8zM6.095 3.28a.557.557 0 0 1 .705-.335l1.178.393 1.171-.393a.573.573 0 0 1 .706.335l1.287 3.433H4.815l1.28-3.433zm4.414 9.062a1.97 1.97 0 0 1-1.956-1.804c-.546-.349-.99-.13-1.164-.014a1.96 1.96 0 0 1-1.956 1.81 1.977 1.977 0 0 1-1.971-1.97c0-1.084.887-1.971 1.97-1.971.932 0 1.71.647 1.913 1.52a1.547 1.547 0 0 1 1.237.007 1.97 1.97 0 0 1 1.913-1.527c1.083 0 1.97.887 1.97 1.97a1.948 1.948 0 0 1-1.956 1.979zm2.538-4.502H2.91v-.567h10.138v.567z"/><circle cx="10.509" cy="10.371" r="1.411"/></g></svg>

After

Width:  |  Height:  |  Size: 715 B

View file

@ -0,0 +1 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><circle cx="8" cy="8" r="8" fill="#fff"/><path d="M13 7.164H3v.538h10v-.538zm-1.878-.537L9.85 3.35a.562.562 0 0 0-.694-.323L8 3.403l-1.161-.376a.562.562 0 0 0-.695.323L4.878 6.627h6.244zM10.5 8.239c-.922 0-1.689.623-1.889 1.456a1.57 1.57 0 0 0-1.222-.005A1.934 1.934 0 0 0 5.5 8.239c-1.072 0-1.944.844-1.944 1.88C3.556 11.157 4.428 12 5.5 12c1.022 0 1.85-.763 1.928-1.73.166-.113.605-.322 1.144.01.09.962.911 1.72 1.928 1.72 1.072 0 1.944-.844 1.944-1.88 0-1.037-.872-1.881-1.944-1.881zm-5 3.224c-.767 0-1.389-.602-1.389-1.343 0-.742.622-1.344 1.389-1.344s1.389.602 1.389 1.344c0 .741-.622 1.343-1.389 1.343zm5 0c-.767 0-1.389-.602-1.389-1.343 0-.742.622-1.344 1.389-1.344s1.389.602 1.389 1.344c0 .741-.622 1.343-1.389 1.343z" fill="#E51C23"/></svg>

After

Width:  |  Height:  |  Size: 845 B

View file

@ -0,0 +1 @@
<svg width="24" height="24" xmlns="http://www.w3.org/2000/svg"><g fill="none" fill-rule="evenodd"><path d="M0 0h24v24H0V0z"/><path d="M14 2H6c-1.1 0-1.99.9-1.99 2L4 20c0 1.1.89 2 1.99 2H18c1.1 0 2-.9 2-2V8l-6-6zm-1 7V3.5L18.5 9H13zM6 4h5v16H6V4zm5 7h7v9h-7v-9z" fill="#1A73E8"/></g></svg>

After

Width:  |  Height:  |  Size: 289 B

View file

@ -0,0 +1,388 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/search/search.h"
#include <stddef.h>
#include <string>
#include "base/command_line.h"
#include "base/feature_list.h"
#include "base/metrics/histogram_macros.h"
#include "build/build_config.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/search_engines/template_url_service_factory.h"
#include "chrome/browser/search_engines/ui_thread_search_terms_data.h"
#include "chrome/common/chrome_switches.h"
#include "chrome/common/url_constants.h"
#include "components/google/core/common/google_util.h"
#include "components/search/ntp_features.h"
#include "components/search/search.h"
#include "components/search_engines/search_engine_type.h"
#include "components/search_engines/template_url_service.h"
#include "content/public/browser/navigation_entry.h"
#include "content/public/browser/render_frame_host.h"
#include "content/public/browser/render_process_host.h"
#include "content/public/browser/web_contents.h"
#include "url/gurl.h"
#if BUILDFLAG(ENABLE_SUPERVISED_USERS)
#include "chrome/browser/supervised_user/supervised_user_service.h"
#include "chrome/browser/supervised_user/supervised_user_service_factory.h"
#include "chrome/browser/supervised_user/supervised_user_url_filter.h" // nogncheck
#endif
#if !BUILDFLAG(IS_ANDROID)
#include "chrome/browser/search/instant_service.h"
#include "chrome/browser/search/instant_service_factory.h"
#include "chrome/browser/ui/webui/new_tab_page/new_tab_page_ui.h"
#include "chrome/browser/ui/webui/new_tab_page_third_party/new_tab_page_third_party_ui.h"
#endif
namespace search {
namespace {
const char kServiceWorkerFileName[] = "newtab-serviceworker.js";
bool MatchesOrigin(const GURL& my_url, const GURL& other_url) {
return my_url.scheme_piece() == other_url.scheme_piece() &&
my_url.host_piece() == other_url.host_piece() &&
my_url.port() == other_url.port();
}
} // namespace
// Returns true if |my_url| matches |other_url| in terms of origin (i.e. host,
// port, and scheme) and path.
// Defined outside of the anonymous namespace so that it's accessible to unit
// tests.
bool MatchesOriginAndPath(const GURL& my_url, const GURL& other_url) {
return MatchesOrigin(my_url, other_url) &&
my_url.path_piece() == other_url.path_piece();
}
namespace {
// Status of the New Tab URL for the default Search provider. NOTE: Used in a
// UMA histogram so values should only be added at the end and not reordered.
enum NewTabURLState {
// Valid URL that should be used.
NEW_TAB_URL_VALID = 0,
// Corrupt state (e.g. no profile or template url).
NEW_TAB_URL_BAD = 1,
// URL should not be used because in incognito window.
NEW_TAB_URL_INCOGNITO = 2,
// No New Tab URL set for provider.
NEW_TAB_URL_NOT_SET = 3,
// URL is not secure.
NEW_TAB_URL_INSECURE = 4,
// URL should not be used because Suggest is disabled.
// Not used anymore, see crbug.com/340424.
// NEW_TAB_URL_SUGGEST_OFF = 5,
// URL should not be used because it is blocked for a supervised user.
NEW_TAB_URL_BLOCKED = 6,
NEW_TAB_URL_MAX
};
const TemplateURL* GetDefaultSearchProviderTemplateURL(Profile* profile) {
if (profile) {
TemplateURLService* template_url_service =
TemplateURLServiceFactory::GetForProfile(profile);
if (template_url_service)
return template_url_service->GetDefaultSearchProvider();
}
return nullptr;
}
bool IsMatchingServiceWorker(const GURL& my_url, const GURL& document_url) {
// The origin should match.
if (!MatchesOrigin(my_url, document_url))
return false;
// The url filename should be the new tab page ServiceWorker.
std::string my_filename = my_url.ExtractFileName();
if (my_filename != kServiceWorkerFileName)
return false;
// The paths up to the filenames should be the same.
std::string my_path_without_filename = my_url.path();
my_path_without_filename = my_path_without_filename.substr(
0, my_path_without_filename.length() - my_filename.length());
std::string document_filename = document_url.ExtractFileName();
std::string document_path_without_filename = document_url.path();
document_path_without_filename = document_path_without_filename.substr(
0, document_path_without_filename.length() - document_filename.length());
return my_path_without_filename == document_path_without_filename;
}
// Returns true if |url| matches the NTP URL or the URL of the NTP's associated
// service worker.
bool IsNTPOrRelatedURLHelper(const GURL& url, Profile* profile) {
if (!url.is_valid())
return false;
const GURL new_tab_url(GetNewTabPageURL(profile));
return new_tab_url.is_valid() && (MatchesOriginAndPath(url, new_tab_url) ||
IsMatchingServiceWorker(url, new_tab_url));
}
bool IsURLAllowedForSupervisedUser(const GURL& url, Profile* profile) {
#if BUILDFLAG(ENABLE_SUPERVISED_USERS)
// If this isn't a supervised child user, skip the URL filter check, since it
// can be fairly expensive.
if (!profile->IsChild())
return true;
SupervisedUserService* supervised_user_service =
SupervisedUserServiceFactory::GetForProfile(profile);
SupervisedUserURLFilter* url_filter = supervised_user_service->GetURLFilter();
if (url_filter->GetFilteringBehaviorForURL(url) ==
SupervisedUserURLFilter::BLOCK) {
return false;
}
#endif
return true;
}
bool ShouldShowLocalNewTab(Profile* profile) {
#if !BUILDFLAG(IS_ANDROID)
return DefaultSearchProviderIsGoogle(profile);
#else
return true;
#endif
}
// Used to look up the URL to use for the New Tab page. Also tracks how we
// arrived at that URL so it can be logged with UMA.
struct NewTabURLDetails {
NewTabURLDetails(const GURL& url, NewTabURLState state)
: url(url), state(state) {}
static NewTabURLDetails ForProfile(Profile* profile) {
// Incognito and Guest profiles have their own New Tab.
// This function may also be called by other off-the-record profiles that
// can exceptionally open a browser window.
// See OTRProfileID::AllowsBrowserWindows() for more context.
if (profile->IsOffTheRecord())
return NewTabURLDetails(GURL(), NEW_TAB_URL_INCOGNITO);
#if BUILDFLAG(IS_ANDROID)
const GURL local_url;
#else
const GURL local_url(DefaultSearchProviderIsGoogle(profile)
? chrome::kChromeUINewTabPageURL
: chrome::kChromeUINewTabPageThirdPartyURL);
#endif
if (ShouldShowLocalNewTab(profile))
return NewTabURLDetails(local_url, NEW_TAB_URL_VALID);
const TemplateURL* template_url =
GetDefaultSearchProviderTemplateURL(profile);
if (!profile || !template_url)
return NewTabURLDetails(local_url, NEW_TAB_URL_BAD);
GURL search_provider_url(template_url->new_tab_url_ref().ReplaceSearchTerms(
TemplateURLRef::SearchTermsArgs(std::u16string()),
UIThreadSearchTermsData()));
if (!search_provider_url.is_valid())
return NewTabURLDetails(local_url, NEW_TAB_URL_NOT_SET);
if (!search_provider_url.SchemeIsCryptographic())
return NewTabURLDetails(local_url, NEW_TAB_URL_INSECURE);
if (!IsURLAllowedForSupervisedUser(search_provider_url, profile))
return NewTabURLDetails(local_url, NEW_TAB_URL_BLOCKED);
return NewTabURLDetails(search_provider_url, NEW_TAB_URL_VALID);
}
const GURL url;
const NewTabURLState state;
};
bool IsRenderedInInstantProcess(content::WebContents* contents,
Profile* profile) {
#if BUILDFLAG(IS_ANDROID)
return false;
#else
content::RenderProcessHost* process_host =
contents->GetPrimaryMainFrame()->GetProcess();
if (!process_host)
return false;
const InstantService* instant_service =
InstantServiceFactory::GetForProfile(profile);
if (!instant_service)
return false;
return instant_service->IsInstantProcess(process_host->GetID());
#endif
}
} // namespace
bool DefaultSearchProviderIsGoogle(Profile* profile) {
return DefaultSearchProviderIsGoogle(
TemplateURLServiceFactory::GetForProfile(profile));
}
bool IsNTPOrRelatedURL(const GURL& url, Profile* profile) {
if (!url.is_valid())
return false;
if (!IsInstantExtendedAPIEnabled())
return url == chrome::kChromeUINewTabURL;
return profile && IsNTPOrRelatedURLHelper(url, profile);
}
bool IsNTPURL(const GURL& url) {
if (url.SchemeIs(chrome::kChromeSearchScheme) &&
url.host_piece() == chrome::kChromeSearchRemoteNtpHost) {
return true;
}
#if BUILDFLAG(IS_ANDROID)
return false;
#else
return NewTabPageUI::IsNewTabPageOrigin(url) ||
NewTabPageThirdPartyUI::IsNewTabPageOrigin(url);
#endif
}
bool IsInstantNTP(content::WebContents* contents) {
if (!contents)
return false;
content::NavigationEntry* entry =
contents->GetController().GetLastCommittedEntry();
if (!entry)
entry = contents->GetController().GetVisibleEntry();
return NavEntryIsInstantNTP(contents, entry);
}
bool NavEntryIsInstantNTP(content::WebContents* contents,
content::NavigationEntry* entry) {
if (!contents || !entry || !IsInstantExtendedAPIEnabled())
return false;
Profile* profile = Profile::FromBrowserContext(contents->GetBrowserContext());
if (!IsRenderedInInstantProcess(contents, profile))
return false;
return IsInstantNTPURL(entry->GetURL(), profile);
}
bool IsInstantNTPURL(const GURL& url, Profile* profile) {
if (MatchesOrigin(url, GURL(chrome::kChromeUINewTabPageURL)))
return true;
if (!IsInstantExtendedAPIEnabled())
return false;
GURL new_tab_url(GetNewTabPageURL(profile));
return new_tab_url.is_valid() && MatchesOriginAndPath(url, new_tab_url);
}
GURL GetNewTabPageURL(Profile* profile) {
return NewTabURLDetails::ForProfile(profile).url;
}
#if !BUILDFLAG(IS_ANDROID)
bool ShouldAssignURLToInstantRenderer(const GURL& url, Profile* profile) {
if (!url.is_valid() || !profile || !IsInstantExtendedAPIEnabled() ||
url.SchemeIs(content::kChromeUIScheme)) {
return false;
}
return IsNTPOrRelatedURLHelper(url, profile) ||
url.SchemeIs(chrome::kChromeSearchScheme);
}
bool ShouldUseProcessPerSiteForInstantSiteURL(const GURL& site_url,
Profile* profile) {
return ShouldAssignURLToInstantRenderer(site_url, profile) &&
site_url.host_piece() == chrome::kChromeSearchRemoteNtpHost;
}
GURL GetEffectiveURLForInstant(const GURL& url, Profile* profile) {
CHECK(ShouldAssignURLToInstantRenderer(url, profile))
<< "Error granting Instant access.";
if (url.SchemeIs(chrome::kChromeSearchScheme))
return url;
// Replace the scheme with "chrome-search:", and clear the port, since
// chrome-search is a scheme without port.
GURL::Replacements replacements;
replacements.SetSchemeStr(chrome::kChromeSearchScheme);
replacements.ClearPort();
// If this is the URL for a server-provided NTP, replace the host with
// "remote-ntp".
std::string remote_ntp_host(chrome::kChromeSearchRemoteNtpHost);
NewTabURLDetails details = NewTabURLDetails::ForProfile(profile);
if (details.state == NEW_TAB_URL_VALID &&
(MatchesOriginAndPath(url, details.url) ||
IsMatchingServiceWorker(url, details.url))) {
replacements.SetHostStr(remote_ntp_host);
}
return url.ReplaceComponents(replacements);
}
bool HandleNewTabURLRewrite(GURL* url,
content::BrowserContext* browser_context) {
if (!IsInstantExtendedAPIEnabled())
return false;
if (!(url->SchemeIs(content::kChromeUIScheme) &&
url->host() == chrome::kChromeUINewTabHost) &&
!(url->SchemeIs(chrome::kChromeSearchScheme) &&
url->host_piece() == chrome::kChromeSearchLocalNtpHost)) {
return false;
}
Profile* profile = Profile::FromBrowserContext(browser_context);
NewTabURLDetails details(NewTabURLDetails::ForProfile(profile));
UMA_HISTOGRAM_ENUMERATION("NewTabPage.URLState",
details.state, NEW_TAB_URL_MAX);
if (details.url.is_valid()) {
*url = details.url;
return true;
}
return false;
}
bool HandleNewTabURLReverseRewrite(GURL* url,
content::BrowserContext* browser_context) {
if (!IsInstantExtendedAPIEnabled())
return false;
// Do nothing in incognito.
Profile* profile = Profile::FromBrowserContext(browser_context);
DCHECK(profile);
if (profile->IsOffTheRecord())
return false;
if (IsInstantNTPURL(*url, profile)) {
*url = GURL(chrome::kChromeUINewTabURL);
return true;
}
return false;
}
#endif // !BUILDFLAG(IS_ANDROID)
} // namespace search

View file

@ -0,0 +1,799 @@
// Copyright (c) 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/shell_integration_linux.h"
#include <fcntl.h>
#include <stddef.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <memory>
#include <sstream>
#include <string>
#include <utility>
#include <vector>
#include "base/base_paths.h"
#include "base/command_line.h"
#include "base/environment.h"
#include "base/files/file_enumerator.h"
#include "base/files/file_path.h"
#include "base/files/file_util.h"
#include "base/i18n/file_util_icu.h"
#include "base/logging.h"
#include "base/memory/ref_counted_memory.h"
#include "base/nix/xdg_util.h"
#include "base/path_service.h"
#include "base/posix/eintr_wrapper.h"
#include "base/process/kill.h"
#include "base/process/launch.h"
#include "base/strings/string_number_conversions.h"
#include "base/strings/string_tokenizer.h"
#include "base/strings/string_util.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
#include "base/threading/scoped_blocking_call.h"
#include "base/threading/thread.h"
#include "base/threading/thread_restrictions.h"
#include "build/branding_buildflags.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/shell_integration.h"
#include "chrome/browser/web_applications/os_integration/web_app_shortcut.h"
#include "chrome/browser/web_applications/web_app_helpers.h"
#include "chrome/common/buildflags.h"
#include "chrome/common/channel_info.h"
#include "chrome/common/chrome_constants.h"
#include "chrome/common/chrome_switches.h"
#include "chrome/grit/chrome_unscaled_resources.h"
#include "components/version_info/version_info.h"
#include "third_party/libxml/chromium/xml_writer.h"
#include "third_party/re2/src/re2/re2.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/gfx/image/image_family.h"
#include "ui/ozone/public/ozone_platform.h"
#include "ui/ozone/public/platform_utils.h"
#include "url/gurl.h"
#if defined(USE_GLIB)
#include <glib.h>
#endif
namespace shell_integration_linux {
const char kXdgSettings[] = "xdg-settings";
const char kXdgSettingsDefaultBrowser[] = "default-web-browser";
const char kXdgSettingsDefaultSchemeHandler[] = "default-url-scheme-handler";
// Utility function to get the path to the version of a script shipped with
// Chrome. |script| gives the name of the script. |chrome_version| returns the
// path to the Chrome version of the script, and the return value of the
// function is true if the function is successful and the Chrome version is
// not the script found on the PATH.
bool GetChromeVersionOfScript(const std::string& script,
std::string* chrome_version) {
// Get the path to the Chrome version.
base::FilePath chrome_dir;
if (!base::PathService::Get(base::DIR_EXE, &chrome_dir))
return false;
base::FilePath chrome_version_path = chrome_dir.Append(script);
*chrome_version = chrome_version_path.value();
// Check if this is different to the one on path.
std::vector<std::string> argv;
argv.push_back("which");
argv.push_back(script);
std::string path_version;
if (base::GetAppOutput(base::CommandLine(argv), &path_version)) {
// Remove trailing newline
path_version.erase(path_version.length() - 1, 1);
base::FilePath path_version_path(path_version);
return (chrome_version_path != path_version_path);
}
return false;
}
// Value returned by xdg-settings if it can't understand our request.
const int EXIT_XDG_SETTINGS_SYNTAX_ERROR = 1;
// We delegate the difficulty of setting the default browser and default url
// scheme handler in Linux desktop environments to an xdg utility, xdg-settings.
// When calling this script we first try to use the script on PATH. If that
// fails we then try to use the script that we have included. This gives
// scripts on the system priority over ours, as distribution vendors may have
// tweaked the script, but still allows our copy to be used if the script on the
// system fails, as the system copy may be missing capabilities of the Chrome
// copy.
// If |protocol| is empty this function sets Chrome as the default browser,
// otherwise it sets Chrome as the default handler application for |protocol|.
bool SetDefaultWebClient(const std::string& protocol) {
#if BUILDFLAG(IS_CHROMEOS_ASH)
return true;
#else
std::unique_ptr<base::Environment> env(base::Environment::Create());
std::vector<std::string> argv;
argv.push_back(kXdgSettings);
argv.push_back("set");
if (protocol.empty()) {
argv.push_back(kXdgSettingsDefaultBrowser);
} else {
argv.push_back(kXdgSettingsDefaultSchemeHandler);
argv.push_back(protocol);
}
argv.push_back(chrome::GetDesktopName(env.get()));
int exit_code;
bool ran_ok = LaunchXdgUtility(argv, &exit_code);
if (ran_ok && exit_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
ran_ok = LaunchXdgUtility(argv, &exit_code);
}
}
return ran_ok && exit_code == EXIT_SUCCESS;
#endif
}
// If |protocol| is empty this function checks if Chrome is the default browser,
// otherwise it checks if Chrome is the default handler application for
// |protocol|.
shell_integration::DefaultWebClientState GetIsDefaultWebClient(
const std::string& protocol) {
#if BUILDFLAG(IS_CHROMEOS_ASH)
return shell_integration::UNKNOWN_DEFAULT;
#else
base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
base::BlockingType::MAY_BLOCK);
std::unique_ptr<base::Environment> env(base::Environment::Create());
std::vector<std::string> argv;
argv.push_back(kXdgSettings);
argv.push_back("check");
if (protocol.empty()) {
argv.push_back(kXdgSettingsDefaultBrowser);
} else {
argv.push_back(kXdgSettingsDefaultSchemeHandler);
argv.push_back(protocol);
}
argv.push_back(chrome::GetDesktopName(env.get()));
std::string reply;
int success_code;
bool ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
&success_code);
if (ran_ok && success_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
&success_code);
}
}
if (!ran_ok || success_code != EXIT_SUCCESS) {
// xdg-settings failed: we can't determine or set the default browser.
return shell_integration::UNKNOWN_DEFAULT;
}
// Allow any reply that starts with "yes".
return base::StartsWith(reply, "yes", base::CompareCase::SENSITIVE)
? shell_integration::IS_DEFAULT
: shell_integration::NOT_DEFAULT;
#endif
}
// https://wiki.gnome.org/Projects/GnomeShell/ApplicationBased
// The WM_CLASS property should be set to the same as the *.desktop file without
// the .desktop extension. We cannot simply use argv[0] in this case, because
// on the stable channel, the executable name is google-chrome-stable, but the
// desktop file is google-chrome.desktop.
std::string GetDesktopBaseName(const std::string& desktop_file_name) {
static const char kDesktopExtension[] = ".desktop";
if (base::EndsWith(desktop_file_name, kDesktopExtension,
base::CompareCase::SENSITIVE)) {
return desktop_file_name.substr(
0, desktop_file_name.length() - strlen(kDesktopExtension));
}
return desktop_file_name;
}
namespace {
#if defined(USE_GLIB)
// Quote a string such that it appears as one verbatim argument for the Exec
// key in a desktop file.
std::string QuoteArgForDesktopFileExec(const std::string& arg) {
// http://standards.freedesktop.org/desktop-entry-spec/latest/ar01s06.html
// Quoting is only necessary if the argument has a reserved character.
if (arg.find_first_of(" \t\n\"'\\><~|&;$*?#()`") == std::string::npos)
return arg; // No quoting necessary.
std::string quoted = "\"";
for (size_t i = 0; i < arg.size(); ++i) {
// Note that the set of backslashed characters is smaller than the
// set of reserved characters.
switch (arg[i]) {
case '"':
case '`':
case '$':
case '\\':
quoted += '\\';
break;
}
quoted += arg[i];
}
quoted += '"';
return quoted;
}
// Quote a command line so it is suitable for use as the Exec key in a desktop
// file. Note: This should be used instead of GetCommandLineString, which does
// not properly quote the string; this function is designed for the Exec key.
std::string QuoteCommandLineForDesktopFileExec(
const base::CommandLine& command_line) {
// http://standards.freedesktop.org/desktop-entry-spec/latest/ar01s06.html
std::string quoted_path;
const base::CommandLine::StringVector& argv = command_line.argv();
for (auto i = argv.begin(); i != argv.end(); ++i) {
if (i != argv.begin())
quoted_path += " ";
quoted_path += QuoteArgForDesktopFileExec(*i);
}
return quoted_path;
}
#endif
#if defined(USE_GLIB)
const char kDesktopEntry[] = "Desktop Entry";
const char kXdgOpenShebang[] = "#!/usr/bin/env xdg-open";
void SetActionsForDesktopApplication(
const base::CommandLine& command_line,
GKeyFile* key_file,
std::set<web_app::DesktopActionInfo> action_info) {
if (action_info.empty())
return;
std::vector<std::string> action_ids;
for (const auto& info : action_info) {
action_ids.push_back(info.id);
}
std::string joined_action_ids = base::JoinString(action_ids, ";");
g_key_file_set_string(key_file, kDesktopEntry, "Actions",
joined_action_ids.c_str());
for (const auto& info : action_info) {
std::string section_title = "Desktop Action " + info.id;
g_key_file_set_string(key_file, section_title.c_str(), "Name",
info.name.c_str());
std::string launch_url_str = info.exec_launch_url.spec();
// Escape % as %%.
RE2::GlobalReplace(&launch_url_str, "%", "%%");
base::CommandLine current_cmd(command_line);
current_cmd.AppendSwitchASCII(switches::kAppLaunchUrlForShortcutsMenuItem,
launch_url_str);
g_key_file_set_string(
key_file, section_title.c_str(), "Exec",
QuoteCommandLineForDesktopFileExec(current_cmd).c_str());
}
}
#endif
} // namespace
// Allows LaunchXdgUtility to join a process.
// thread_restrictions.h assumes it to be in shell_integration_linux namespace.
class LaunchXdgUtilityScopedAllowBaseSyncPrimitives
: public base::ScopedAllowBaseSyncPrimitives {};
bool LaunchXdgUtility(const std::vector<std::string>& argv, int* exit_code) {
// xdg-settings internally runs xdg-mime, which uses mv to move newly-created
// files on top of originals after making changes to them. In the event that
// the original files are owned by another user (e.g. root, which can happen
// if they are updated within sudo), mv will prompt the user to confirm if
// standard input is a terminal (otherwise it just does it). So make sure it's
// not, to avoid locking everything up waiting for mv.
*exit_code = EXIT_FAILURE;
int devnull = open("/dev/null", O_RDONLY);
if (devnull < 0)
return false;
base::LaunchOptions options;
options.fds_to_remap.push_back(std::make_pair(devnull, STDIN_FILENO));
base::Process process = base::LaunchProcess(argv, options);
close(devnull);
if (!process.IsValid())
return false;
LaunchXdgUtilityScopedAllowBaseSyncPrimitives allow_base_sync_primitives;
return process.WaitForExit(exit_code);
}
std::string GetWMClassFromAppName(std::string app_name) {
base::i18n::ReplaceIllegalCharactersInPath(&app_name, '_');
base::TrimString(app_name, "_", &app_name);
return app_name;
}
std::string GetXdgAppIdForWebApp(std::string app_name,
const base::FilePath& profile_path) {
if (base::StartsWith(app_name, web_app::kCrxAppPrefix))
app_name = app_name.substr(strlen(web_app::kCrxAppPrefix));
return GetDesktopBaseName(
web_app::GetAppShortcutFilename(profile_path, app_name).AsUTF8Unsafe());
}
base::FilePath GetDataWriteLocation(base::Environment* env) {
return base::nix::GetXDGDirectory(env, "XDG_DATA_HOME", ".local/share");
}
std::vector<base::FilePath> GetDataSearchLocations(base::Environment* env) {
base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
base::BlockingType::MAY_BLOCK);
std::vector<base::FilePath> search_paths;
base::FilePath write_location = GetDataWriteLocation(env);
search_paths.push_back(write_location);
std::string xdg_data_dirs;
if (env->GetVar("XDG_DATA_DIRS", &xdg_data_dirs) && !xdg_data_dirs.empty()) {
base::StringTokenizer tokenizer(xdg_data_dirs, ":");
while (tokenizer.GetNext()) {
search_paths.emplace_back(tokenizer.token_piece());
}
} else {
search_paths.push_back(base::FilePath("/usr/local/share"));
search_paths.push_back(base::FilePath("/usr/share"));
}
return search_paths;
}
namespace internal {
// Get the value of NoDisplay from the [Desktop Entry] section of a .desktop
// file, given in |shortcut_contents|. If the key is not found, returns false.
bool GetNoDisplayFromDesktopFile(const std::string& shortcut_contents) {
#if defined(USE_GLIB)
// An empty file causes a crash with glib <= 2.32, so special case here.
if (shortcut_contents.empty())
return false;
GKeyFile* key_file = g_key_file_new();
GError* err = NULL;
if (!g_key_file_load_from_data(key_file, shortcut_contents.c_str(),
shortcut_contents.size(), G_KEY_FILE_NONE,
&err)) {
LOG(WARNING) << "Unable to read desktop file template: " << err->message;
g_error_free(err);
g_key_file_free(key_file);
return false;
}
bool nodisplay = false;
char* nodisplay_c_string = g_key_file_get_string(key_file, kDesktopEntry,
"NoDisplay", &err);
if (nodisplay_c_string) {
if (!g_strcmp0(nodisplay_c_string, "true"))
nodisplay = true;
g_free(nodisplay_c_string);
} else {
g_error_free(err);
}
g_key_file_free(key_file);
return nodisplay;
#else
NOTIMPLEMENTED();
return false;
#endif
}
// Gets the path to the Chrome executable or wrapper script.
// Returns an empty path if the executable path could not be found, which should
// never happen.
base::FilePath GetChromeExePath() {
// Try to get the name of the wrapper script that launched Chrome.
std::unique_ptr<base::Environment> environment(base::Environment::Create());
std::string wrapper_script;
if (environment->GetVar("CHROME_WRAPPER", &wrapper_script))
return base::FilePath(wrapper_script);
// Just return the name of the executable path for Chrome.
base::FilePath chrome_exe_path;
base::PathService::Get(base::FILE_EXE, &chrome_exe_path);
return chrome_exe_path;
}
std::string GetProgramClassName(const base::CommandLine& command_line,
const std::string& desktop_file_name) {
std::string class_name = GetDesktopBaseName(desktop_file_name);
std::string user_data_dir =
command_line.GetSwitchValueNative(switches::kUserDataDir);
// If the user launches with e.g. --user-data-dir=/tmp/my-user-data, set the
// class name to "Chrome (/tmp/my-user-data)". The class name will show up in
// the alt-tab list in gnome-shell if you're running a binary that doesn't
// have a matching .desktop file.
return user_data_dir.empty()
? class_name
: class_name + " (" + user_data_dir + ")";
}
std::string GetProgramClassClass(const base::CommandLine& command_line,
const std::string& desktop_file_name) {
if (command_line.HasSwitch(switches::kWmClass))
return command_line.GetSwitchValueASCII(switches::kWmClass);
std::string desktop_base_name = GetDesktopBaseName(desktop_file_name);
if (auto* platform_utils =
ui::OzonePlatform::GetInstance()->GetPlatformUtils()) {
return platform_utils->GetWmWindowClass(desktop_base_name);
}
if (!desktop_base_name.empty()) {
// Capitalize the first character like gtk does.
desktop_base_name[0] = base::ToUpperASCII(desktop_base_name[0]);
}
return desktop_base_name;
}
} // namespace internal
std::string GetProgramClassName() {
std::unique_ptr<base::Environment> env(base::Environment::Create());
return internal::GetProgramClassName(*base::CommandLine::ForCurrentProcess(),
chrome::GetDesktopName(env.get()));
}
std::string GetProgramClassClass() {
std::unique_ptr<base::Environment> env(base::Environment::Create());
return internal::GetProgramClassClass(*base::CommandLine::ForCurrentProcess(),
chrome::GetDesktopName(env.get()));
}
std::string GetIconName() {
#if BUILDFLAG(GOOGLE_CHROME_BRANDING)
return "google-chrome";
#else // BUILDFLAG(CHROMIUM_BRANDING)
return "Thorium Browser";
#endif
}
bool GetExistingShortcutContents(base::Environment* env,
const base::FilePath& desktop_filename,
std::string* output) {
base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
base::BlockingType::MAY_BLOCK);
std::vector<base::FilePath> search_paths = GetDataSearchLocations(env);
for (std::vector<base::FilePath>::const_iterator i = search_paths.begin();
i != search_paths.end(); ++i) {
base::FilePath path = i->Append("applications").Append(desktop_filename);
VLOG(1) << "Looking for desktop file in " << path.value();
if (base::PathExists(path)) {
VLOG(1) << "Found desktop file at " << path.value();
return base::ReadFileToString(path, output);
}
}
return false;
}
base::FilePath GetWebShortcutFilename(const GURL& url) {
// Use a prefix, because xdg-desktop-menu requires it.
std::string filename =
std::string(chrome::kBrowserProcessExecutableName) + "-" + url.spec();
base::i18n::ReplaceIllegalCharactersInPath(&filename, '_');
base::FilePath desktop_path;
if (!base::PathService::Get(base::DIR_USER_DESKTOP, &desktop_path))
return base::FilePath();
base::FilePath filepath = desktop_path.Append(filename);
base::FilePath alternative_filepath(filepath.value() + ".desktop");
for (size_t i = 1; i < 100; ++i) {
if (base::PathExists(base::FilePath(alternative_filepath))) {
alternative_filepath = base::FilePath(
filepath.value() + "_" + base::NumberToString(i) + ".desktop");
} else {
return base::FilePath(alternative_filepath).BaseName();
}
}
return base::FilePath();
}
std::vector<base::FilePath> GetExistingProfileShortcutFilenames(
const base::FilePath& profile_path,
const base::FilePath& directory) {
base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
base::BlockingType::MAY_BLOCK);
// Use a prefix, because xdg-desktop-menu requires it.
std::string prefix(chrome::kBrowserProcessExecutableName);
prefix.append("-");
std::string suffix("-");
suffix.append(profile_path.BaseName().value());
base::i18n::ReplaceIllegalCharactersInPath(&suffix, '_');
// Spaces in filenames break xdg-desktop-menu
// (see https://bugs.freedesktop.org/show_bug.cgi?id=66605).
base::ReplaceChars(suffix, " ", "_", &suffix);
std::string glob = prefix + "*" + suffix + ".desktop";
base::FileEnumerator files(directory, false, base::FileEnumerator::FILES,
glob);
base::FilePath shortcut_file = files.Next();
std::vector<base::FilePath> shortcut_paths;
while (!shortcut_file.empty()) {
shortcut_paths.push_back(shortcut_file.BaseName());
shortcut_file = files.Next();
}
return shortcut_paths;
}
std::string GetDesktopFileContents(
const base::FilePath& chrome_exe_path,
const std::string& app_name,
const GURL& url,
const std::string& extension_id,
const std::u16string& title,
const std::string& icon_name,
const base::FilePath& profile_path,
const std::string& categories,
const std::string& mime_type,
bool no_display,
const std::string& run_on_os_login_mode,
std::set<web_app::DesktopActionInfo> action_info) {
base::CommandLine cmd_line = shell_integration::CommandLineArgsForLauncher(
url, extension_id, profile_path, run_on_os_login_mode);
cmd_line.SetProgram(chrome_exe_path);
return GetDesktopFileContentsForCommand(cmd_line, app_name, url, title,
icon_name, categories, mime_type,
no_display, std::move(action_info));
}
std::string GetDesktopFileContentsForCommand(
const base::CommandLine& command_line,
const std::string& app_name,
const GURL& url,
const std::u16string& title,
const std::string& icon_name,
const std::string& categories,
const std::string& mime_type,
bool no_display,
std::set<web_app::DesktopActionInfo> action_info) {
#if defined(USE_GLIB)
// Although not required by the spec, Nautilus on Ubuntu Karmic creates its
// launchers with an xdg-open shebang. Follow that convention.
std::string output_buffer = std::string(kXdgOpenShebang) + "\n";
// See http://standards.freedesktop.org/desktop-entry-spec/latest/
GKeyFile* key_file = g_key_file_new();
// Set keys with fixed values.
g_key_file_set_string(key_file, kDesktopEntry, "Version", "1.0");
g_key_file_set_string(key_file, kDesktopEntry, "Terminal", "false");
g_key_file_set_string(key_file, kDesktopEntry, "Type", "Application");
// Set the "Name" key.
std::string final_title = base::UTF16ToUTF8(title);
// Make sure no endline characters can slip in and possibly introduce
// additional lines (like Exec, which makes it a security risk). Also
// use the URL as a default when the title is empty.
if (final_title.empty() ||
final_title.find("\n") != std::string::npos ||
final_title.find("\r") != std::string::npos) {
final_title = url.spec();
}
g_key_file_set_string(key_file, kDesktopEntry, "Name", final_title.c_str());
base::CommandLine modified_command_line(command_line);
// Set the "MimeType" key.
if (!mime_type.empty() && mime_type.find("\n") == std::string::npos &&
mime_type.find("\r") == std::string::npos) {
g_key_file_set_string(key_file, kDesktopEntry, "MimeType",
mime_type.c_str());
// Some Linux Desktop Environments don't show file handlers unless they
// specify where to place file arguments.
// Note: We only include this parameter if the application is actually able
// to handle files, to prevent it showing up in the list of all applications
// which can handle files.
modified_command_line.AppendArg("%U");
}
// Set the "Exec" key.
std::string final_path =
QuoteCommandLineForDesktopFileExec(modified_command_line);
g_key_file_set_string(key_file, kDesktopEntry, "Exec", final_path.c_str());
// Set the "Icon" key.
if (!icon_name.empty()) {
g_key_file_set_string(key_file, kDesktopEntry, "Icon", icon_name.c_str());
} else {
g_key_file_set_string(key_file, kDesktopEntry, "Icon",
GetIconName().c_str());
}
// Set the "Categories" key.
if (!categories.empty()) {
g_key_file_set_string(
key_file, kDesktopEntry, "Categories", categories.c_str());
}
// Set the "NoDisplay" key.
if (no_display)
g_key_file_set_string(key_file, kDesktopEntry, "NoDisplay", "true");
std::string wmclass = GetWMClassFromAppName(app_name);
g_key_file_set_string(key_file, kDesktopEntry, "StartupWMClass",
wmclass.c_str());
SetActionsForDesktopApplication(command_line, key_file,
std::move(action_info));
gsize length = 0;
gchar* data_dump = g_key_file_to_data(key_file, &length, NULL);
if (data_dump) {
// If strlen(data_dump[0]) == 0, this check will fail.
if (data_dump[0] == '\n') {
// Older versions of glib produce a leading newline. If this is the case,
// remove it to avoid double-newline after the shebang.
output_buffer += (data_dump + 1);
} else {
output_buffer += data_dump;
}
g_free(data_dump);
}
g_key_file_free(key_file);
return output_buffer;
#else
NOTIMPLEMENTED();
return std::string();
#endif
}
std::string GetDirectoryFileContents(const std::u16string& title,
const std::string& icon_name) {
#if defined(USE_GLIB)
// See http://standards.freedesktop.org/desktop-entry-spec/latest/
GKeyFile* key_file = g_key_file_new();
g_key_file_set_string(key_file, kDesktopEntry, "Version", "1.0");
g_key_file_set_string(key_file, kDesktopEntry, "Type", "Directory");
std::string final_title = base::UTF16ToUTF8(title);
g_key_file_set_string(key_file, kDesktopEntry, "Name", final_title.c_str());
if (!icon_name.empty()) {
g_key_file_set_string(key_file, kDesktopEntry, "Icon", icon_name.c_str());
} else {
g_key_file_set_string(key_file, kDesktopEntry, "Icon",
GetIconName().c_str());
}
gsize length = 0;
gchar* data_dump = g_key_file_to_data(key_file, &length, NULL);
std::string output_buffer;
if (data_dump) {
// If strlen(data_dump[0]) == 0, this check will fail.
if (data_dump[0] == '\n') {
// Older versions of glib produce a leading newline. If this is the case,
// remove it to avoid double-newline after the shebang.
output_buffer += (data_dump + 1);
} else {
output_buffer += data_dump;
}
g_free(data_dump);
}
g_key_file_free(key_file);
return output_buffer;
#else
NOTIMPLEMENTED();
return std::string();
#endif
}
base::FilePath GetMimeTypesRegistrationFilename(
const base::FilePath& profile_path,
const web_app::AppId& app_id) {
DCHECK(!profile_path.empty() && !app_id.empty());
// Use a prefix to clearly group files created by Chrome.
std::string filename = base::StringPrintf(
"%s-%s-%s%s", chrome::kBrowserProcessExecutableName, app_id.c_str(),
profile_path.BaseName().value().c_str(), ".xml");
// Replace illegal characters and spaces in |filename|.
base::i18n::ReplaceIllegalCharactersInPath(&filename, '_');
base::ReplaceChars(filename, " ", "_", &filename);
return base::FilePath(filename);
}
std::string GetMimeTypesRegistrationFileContents(
const apps::FileHandlers& file_handlers) {
XmlWriter writer;
writer.StartWriting();
writer.StartElement("mime-info");
writer.AddAttribute("xmlns",
"http://www.freedesktop.org/standards/shared-mime-info");
for (const auto& file_handler : file_handlers) {
for (const auto& accept_entry : file_handler.accept) {
writer.StartElement("mime-type");
writer.AddAttribute("type", accept_entry.mime_type);
if (!file_handler.display_name.empty()) {
writer.WriteElement("comment",
base::UTF16ToUTF8(file_handler.display_name));
}
for (const auto& file_extension : accept_entry.file_extensions) {
writer.StartElement("glob");
writer.AddAttribute("pattern", "*" + file_extension);
writer.EndElement(); // "glob"
}
writer.EndElement(); // "mime-type"
}
}
writer.EndElement(); // "mime-info"
writer.StopWriting();
return writer.GetWrittenString();
}
} // namespace shell_integration_linux
namespace shell_integration {
bool SetAsDefaultBrowser() {
return shell_integration_linux::SetDefaultWebClient(std::string());
}
bool SetAsDefaultProtocolClient(const std::string& protocol) {
return shell_integration_linux::SetDefaultWebClient(protocol);
}
DefaultWebClientSetPermission GetDefaultWebClientSetPermission() {
return SET_DEFAULT_UNATTENDED;
}
std::u16string GetApplicationNameForProtocol(const GURL& url) {
return u"xdg-open";
}
DefaultWebClientState GetDefaultBrowser() {
return shell_integration_linux::GetIsDefaultWebClient(std::string());
}
bool IsFirefoxDefaultBrowser() {
std::vector<std::string> argv;
argv.push_back(shell_integration_linux::kXdgSettings);
argv.push_back("get");
argv.push_back(shell_integration_linux::kXdgSettingsDefaultBrowser);
std::string browser;
// We don't care about the return value here.
base::GetAppOutput(base::CommandLine(argv), &browser);
return browser.find("thorium-browser") != std::string::npos;
}
DefaultWebClientState IsDefaultProtocolClient(const std::string& protocol) {
return shell_integration_linux::GetIsDefaultWebClient(protocol);
}
} // namespace shell_integration

View file

@ -0,0 +1,23 @@
// Copyright (c) 2022 Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef CHROME_BROWSER_THORIUM_FLAG_ENTRIES_H_
#define CHROME_BROWSER_THORIUM_FLAG_ENTRIES_H_
{"custom-ntp",
"Custom New Tab Page",
"Allows setting a custom URL for the New Tab Page (NTP). Value can be internal (e.g. `about:blank`), external (e.g. `example.com`), or local (e.g. `file:///tmp/startpage.html`). This applies for incognito windows as well when not set to a `chrome://` internal page.",
kOsDesktop, ORIGIN_LIST_VALUE_TYPE("custom-ntp", "")},
{"hide-sidepanel-button",
"Hide Side Panel Button",
"Hides the Thorium Side Panel Button.",
kOsDesktop, SINGLE_VALUE_TYPE("hide-sidepanel-button")},
{"force-dark-mode",
"Force Dark Mode",
"Enables Dark Mode (like in Incognito windows) for all Thorium instances.",
kOsDesktop, SINGLE_VALUE_TYPE("force-dark-mode")},
{"no-autoplay",
"Disable AutoPlay",
"Disables AutoPlay for all Thorium instances.",
kOsDesktop, SINGLE_VALUE_TYPE("no-autoplay")},
#endif // CHROME_BROWSER_THORIUM_FLAG_ENTRIES_H_

View file

@ -0,0 +1,168 @@
// Copyright (c) 2022 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 "chrome/browser/ui/browser_ui_prefs.h"
#include <memory>
#include "base/numerics/safe_conversions.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/upgrade_detector/upgrade_detector.h"
#include "chrome/common/buildflags.h"
#include "chrome/common/pref_names.h"
#include "components/pref_registry/pref_registry_syncable.h"
#include "components/prefs/pref_registry_simple.h"
#include "components/prefs/pref_service.h"
#include "components/prefs/scoped_user_pref_update.h"
#include "components/translate/core/browser/translate_pref_names.h"
#include "media/media_buildflags.h"
#include "third_party/blink/public/common/peerconnection/webrtc_ip_handling_policy.h"
#if !BUILDFLAG(IS_CHROMEOS_ASH)
#include "ui/accessibility/accessibility_features.h"
#endif
#if defined(OS_WIN)
#include "base/win/windows_version.h"
#endif
namespace {
uint32_t GetHomeButtonAndHomePageIsNewTabPageFlags() {
#if defined(OS_ANDROID)
return PrefRegistry::NO_REGISTRATION_FLAGS;
#else
return user_prefs::PrefRegistrySyncable::SYNCABLE_PREF;
#endif
}
} // namespace
void RegisterBrowserPrefs(PrefRegistrySimple* registry) {
registry->RegisterBooleanPref(prefs::kAllowFileSelectionDialogs, true);
#if !defined(OS_ANDROID)
registry->RegisterIntegerPref(prefs::kRelaunchNotification, 0);
registry->RegisterIntegerPref(
prefs::kRelaunchNotificationPeriod,
base::saturated_cast<int>(
UpgradeDetector::GetDefaultHighAnnoyanceThreshold()
.InMilliseconds()));
registry->RegisterDictionaryPref(prefs::kRelaunchWindow);
#endif // !defined(OS_ANDROID)
#if defined(OS_MAC)
registry->RegisterIntegerPref(
prefs::kMacRestoreLocationPermissionsExperimentCount, 0);
#endif // defined(OS_MAC)
}
void RegisterBrowserUserPrefs(user_prefs::PrefRegistrySyncable* registry) {
registry->RegisterBooleanPref(prefs::kHomePageIsNewTabPage, true,
GetHomeButtonAndHomePageIsNewTabPageFlags());
registry->RegisterBooleanPref(prefs::kShowHomeButton, true,
GetHomeButtonAndHomePageIsNewTabPageFlags());
registry->RegisterInt64Pref(prefs::kDefaultBrowserLastDeclined, 0);
bool reset_check_default = false;
#if defined(OS_WIN)
reset_check_default = base::win::GetVersion() >= base::win::Version::WIN10;
#endif
registry->RegisterBooleanPref(prefs::kResetCheckDefaultBrowser,
reset_check_default);
registry->RegisterBooleanPref(prefs::kWebAppCreateOnDesktop, true);
registry->RegisterBooleanPref(prefs::kWebAppCreateInAppsMenu, true);
registry->RegisterBooleanPref(prefs::kWebAppCreateInQuickLaunchBar, true);
registry->RegisterBooleanPref(
translate::prefs::kOfferTranslateEnabled, true,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
registry->RegisterStringPref(prefs::kCloudPrintEmail, std::string());
registry->RegisterBooleanPref(prefs::kCloudPrintProxyEnabled, true);
registry->RegisterBooleanPref(prefs::kCloudPrintSubmitEnabled, true);
registry->RegisterDictionaryPref(prefs::kBrowserWindowPlacement);
registry->RegisterDictionaryPref(prefs::kBrowserWindowPlacementPopup);
registry->RegisterDictionaryPref(prefs::kAppWindowPlacement);
registry->RegisterBooleanPref(
prefs::kEnableDoNotTrack, true,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
#if !BUILDFLAG(IS_CHROMEOS_ASH) && !defined(OS_ANDROID)
registry->RegisterBooleanPref(prefs::kPrintPreviewUseSystemDefaultPrinter,
false);
#endif
registry->RegisterStringPref(prefs::kWebRTCIPHandlingPolicy,
blink::kWebRTCIPHandlingDefault);
registry->RegisterStringPref(prefs::kWebRTCUDPPortRange, std::string());
registry->RegisterBooleanPref(prefs::kWebRtcEventLogCollectionAllowed, false);
registry->RegisterListPref(prefs::kWebRtcLocalIpsAllowedUrls);
registry->RegisterBooleanPref(prefs::kWebRTCAllowLegacyTLSProtocols, false);
// Dictionaries to keep track of default tasks in the file browser.
registry->RegisterDictionaryPref(
prefs::kDefaultTasksByMimeType,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
registry->RegisterDictionaryPref(
prefs::kDefaultTasksBySuffix,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
// We need to register the type of these preferences in order to query
// them even though they're only typically controlled via policy.
registry->RegisterBooleanPref(prefs::kClearPluginLSODataEnabled, true);
registry->RegisterBooleanPref(prefs::kHideWebStoreIcon, false);
registry->RegisterBooleanPref(prefs::kSharedClipboardEnabled, true);
#if BUILDFLAG(ENABLE_CLICK_TO_CALL)
registry->RegisterBooleanPref(prefs::kClickToCallEnabled, true);
#endif // BUILDFLAG(ENABLE_CLICK_TO_CALL)
#if defined(OS_MAC)
// This really belongs in platform code, but there's no good place to
// initialize it between the time when the AppController is created
// (where there's no profile) and the time the controller gets another
// crack at the start of the main event loop. By that time,
// StartupBrowserCreator has already created the browser window, and it's too
// late: we need the pref to be already initialized. Doing it here also saves
// us from having to hard-code pref registration in the several unit tests
// that use this preference.
registry->RegisterBooleanPref(prefs::kShowUpdatePromotionInfoBar, true);
registry->RegisterBooleanPref(
prefs::kShowFullscreenToolbar, true,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
registry->RegisterBooleanPref(
prefs::kAllowJavascriptAppleEvents, false,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
#else
registry->RegisterBooleanPref(prefs::kFullscreenAllowed, true);
#endif
#if BUILDFLAG(IS_CHROMEOS)
registry->RegisterBooleanPref(prefs::kForceMaximizeOnFirstRun, false);
#endif
registry->RegisterBooleanPref(prefs::kEnterpriseHardwarePlatformAPIEnabled,
false);
registry->RegisterBooleanPref(prefs::kUserFeedbackAllowed, true);
registry->RegisterBooleanPref(
prefs::kExternalProtocolDialogShowAlwaysOpenCheckbox, true);
registry->RegisterBooleanPref(prefs::kScreenCaptureAllowed, true);
registry->RegisterListPref(prefs::kScreenCaptureAllowedByOrigins);
registry->RegisterListPref(prefs::kWindowCaptureAllowedByOrigins);
registry->RegisterListPref(prefs::kTabCaptureAllowedByOrigins);
registry->RegisterListPref(prefs::kSameOriginTabCaptureAllowedByOrigins);
#if !defined(OS_ANDROID)
registry->RegisterBooleanPref(prefs::kCaretBrowsingEnabled, false);
registry->RegisterBooleanPref(prefs::kShowCaretBrowsingDialog, true);
#endif
#if !BUILDFLAG(IS_CHROMEOS_ASH)
registry->RegisterBooleanPref(prefs::kAccessibilityFocusHighlightEnabled,
false);
#endif
registry->RegisterBooleanPref(
prefs::kHttpsOnlyModeEnabled, false,
user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
}

View file

@ -0,0 +1,115 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ui/startup/default_browser_infobar_delegate.h"
#include <memory>
#include "base/bind.h"
#include "base/callback_helpers.h"
#include "base/metrics/histogram_macros.h"
#include "base/metrics/user_metrics.h"
#include "base/threading/thread_task_runner_handle.h"
#include "chrome/app/vector_icons/vector_icons.h"
#include "chrome/browser/infobars/confirm_infobar_creator.h"
#include "chrome/browser/ui/startup/default_browser_prompt.h"
#include "chrome/grit/chromium_strings.h"
#include "chrome/grit/generated_resources.h"
#include "components/infobars/core/infobar.h"
#include "ui/base/l10n/l10n_util.h"
namespace chrome {
// static
void DefaultBrowserInfoBarDelegate::Create(
infobars::ContentInfoBarManager* infobar_manager,
Profile* profile) {
}
DefaultBrowserInfoBarDelegate::DefaultBrowserInfoBarDelegate(Profile* profile)
: profile_(profile) {
// We want the info-bar to stick-around for few seconds and then be hidden
// on the next navigation after that.
base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
FROM_HERE,
base::BindOnce(&DefaultBrowserInfoBarDelegate::AllowExpiry,
weak_factory_.GetWeakPtr()),
base::Seconds(8));
}
DefaultBrowserInfoBarDelegate::~DefaultBrowserInfoBarDelegate() {
if (!action_taken_) {
base::RecordAction(base::UserMetricsAction("DefaultBrowserInfoBar_Ignore"));
UMA_HISTOGRAM_ENUMERATION("DefaultBrowser.InfoBar.UserInteraction",
IGNORE_INFO_BAR,
NUM_INFO_BAR_USER_INTERACTION_TYPES);
}
}
void DefaultBrowserInfoBarDelegate::AllowExpiry() {
should_expire_ = true;
}
infobars::InfoBarDelegate::InfoBarIdentifier
DefaultBrowserInfoBarDelegate::GetIdentifier() const {
return DEFAULT_BROWSER_INFOBAR_DELEGATE;
}
const gfx::VectorIcon& DefaultBrowserInfoBarDelegate::GetVectorIcon() const {
return kProductIcon;
}
bool DefaultBrowserInfoBarDelegate::ShouldExpire(
const NavigationDetails& details) const {
return should_expire_ && ConfirmInfoBarDelegate::ShouldExpire(details);
}
void DefaultBrowserInfoBarDelegate::InfoBarDismissed() {
action_taken_ = true;
// |profile_| may be null in tests.
if (profile_)
DefaultBrowserPromptDeclined(profile_);
base::RecordAction(base::UserMetricsAction("DefaultBrowserInfoBar_Dismiss"));
UMA_HISTOGRAM_ENUMERATION("DefaultBrowser.InfoBar.UserInteraction",
DISMISS_INFO_BAR,
NUM_INFO_BAR_USER_INTERACTION_TYPES);
}
std::u16string DefaultBrowserInfoBarDelegate::GetMessageText() const {
return l10n_util::GetStringUTF16(IDS_DEFAULT_BROWSER_INFOBAR_TEXT);
}
int DefaultBrowserInfoBarDelegate::GetButtons() const {
return BUTTON_OK;
}
std::u16string DefaultBrowserInfoBarDelegate::GetButtonLabel(
InfoBarButton button) const {
DCHECK_EQ(BUTTON_OK, button);
return l10n_util::GetStringUTF16(IDS_DEFAULT_BROWSER_INFOBAR_OK_BUTTON_LABEL);
}
// Setting an app as the default browser doesn't require elevation directly, but
// it does require registering it as the protocol handler for "http", so if
// protocol registration in general requires elevation, this does as well.
bool DefaultBrowserInfoBarDelegate::OKButtonTriggersUACPrompt() const {
return shell_integration::IsElevationNeededForSettingDefaultProtocolClient();
}
bool DefaultBrowserInfoBarDelegate::Accept() {
action_taken_ = true;
base::RecordAction(base::UserMetricsAction("DefaultBrowserInfoBar_Accept"));
UMA_HISTOGRAM_ENUMERATION("DefaultBrowser.InfoBar.UserInteraction",
ACCEPT_INFO_BAR,
NUM_INFO_BAR_USER_INTERACTION_TYPES);
// The worker pointer is reference counted. While it is running, the
// message loops of the FILE and UI thread will hold references to it
// and it will be automatically freed once all its tasks have finished.
base::MakeRefCounted<shell_integration::DefaultBrowserWorker>()
->StartSetAsDefault(base::NullCallback());
return true;
}
} // namespace chrome

View file

@ -0,0 +1,45 @@
// Copyright 2013 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 "chrome/browser/ui/startup/google_api_keys_infobar_delegate.h"
#include <memory>
#include "chrome/browser/infobars/confirm_infobar_creator.h"
#include "chrome/grit/chromium_strings.h"
#include "components/infobars/content/content_infobar_manager.h"
#include "components/infobars/core/infobar.h"
#include "components/strings/grit/components_strings.h"
#include "google_apis/google_api_keys.h"
#include "ui/base/l10n/l10n_util.h"
// static
void GoogleApiKeysInfoBarDelegate::Create(
infobars::ContentInfoBarManager* infobar_manager) {
}
GoogleApiKeysInfoBarDelegate::GoogleApiKeysInfoBarDelegate()
: ConfirmInfoBarDelegate() {
}
infobars::InfoBarDelegate::InfoBarIdentifier
GoogleApiKeysInfoBarDelegate::GetIdentifier() const {
return GOOGLE_API_KEYS_INFOBAR_DELEGATE;
}
std::u16string GoogleApiKeysInfoBarDelegate::GetLinkText() const {
return l10n_util::GetStringUTF16(IDS_LEARN_MORE);
}
GURL GoogleApiKeysInfoBarDelegate::GetLinkURL() const {
return GURL(google_apis::kAPIKeysDevelopersHowToURL);
}
std::u16string GoogleApiKeysInfoBarDelegate::GetMessageText() const {
return l10n_util::GetStringUTF16(IDS_MISSING_GOOGLE_API_KEYS);
}
int GoogleApiKeysInfoBarDelegate::GetButtons() const {
return BUTTON_NONE;
}

View file

@ -0,0 +1,132 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ui/startup/infobar_utils.h"
#include "base/command_line.h"
#include "build/buildflag.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/obsolete_system/obsolete_system.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/session_crashed_bubble.h"
#include "chrome/browser/ui/startup/automation_infobar_delegate.h"
#include "chrome/browser/ui/startup/bad_flags_prompt.h"
#include "chrome/browser/ui/startup/default_browser_prompt.h"
#include "chrome/browser/ui/startup/google_api_keys_infobar_delegate.h"
#include "chrome/browser/ui/startup/obsolete_system_infobar_delegate.h"
#include "chrome/browser/ui/startup/startup_browser_creator.h"
#include "chrome/browser/ui/startup/startup_types.h"
#include "chrome/common/chrome_switches.h"
#include "chrome/common/pref_names.h"
#include "components/infobars/content/content_infobar_manager.h"
#include "components/prefs/pref_service.h"
#include "content/public/common/content_switches.h"
#include "google_apis/google_api_keys.h"
namespace {
bool ShouldShowBadFlagsSecurityWarnings() {
#if !BUILDFLAG(IS_CHROMEOS_ASH)
PrefService* local_state = g_browser_process->local_state();
if (!local_state)
return true;
const auto* pref = local_state->FindPreference(
prefs::kCommandLineFlagSecurityWarningsEnabled);
DCHECK(pref);
// The warnings can only be disabled by policy. Default to show warnings.
if (pref->IsManaged())
return pref->GetValue()->GetBool();
#endif
return true;
}
// This is a separate function to avoid accidentally reading the switch from
// `startup_command_line`.
bool IsAutomationEnabled() {
return base::CommandLine::ForCurrentProcess()->HasSwitch(
switches::kEnableAutomation);
}
// This is a separate function to avoid accidentally reading the switch from
// `startup_command_line`.
bool IsKioskModeEnabled() {
return base::CommandLine::ForCurrentProcess()->HasSwitch(
switches::kKioskMode);
}
} // namespace
void AddInfoBarsIfNecessary(Browser* browser,
Profile* profile,
const base::CommandLine& startup_command_line,
chrome::startup::IsFirstRun is_first_run,
bool is_web_app) {
if (!browser || !profile || browser->tab_strip_model()->count() == 0)
return;
// Show the Automation info bar unless it has been disabled by policy.
bool show_bad_flags_security_warnings = ShouldShowBadFlagsSecurityWarnings();
if (IsAutomationEnabled() && show_bad_flags_security_warnings) {
AutomationInfoBarDelegate::Create();
}
// Do not show any other info bars in Kiosk mode, because it's unlikely that
// the viewer can act upon or dismiss them.
if (IsKioskModeEnabled())
return;
// Web apps should not display the session restore bubble (crbug.com/1264121)
if (!is_web_app && HasPendingUncleanExit(browser->profile()))
SessionCrashedBubble::ShowIfNotOffTheRecordProfile(
browser, /*skip_tab_checking=*/false);
// These info bars are not shown when the browser is being controlled by
// automated tests, so that they don't interfere with tests that assume no
// info bars.
if (!startup_command_line.HasSwitch(switches::kTestType) &&
!IsAutomationEnabled()) {
// The below info bars are only added to the first profile which is
// launched. Other profiles might be restoring the browsing sessions
// asynchronously, so we cannot add the info bars to the focused tabs here.
//
// We cannot use `chrome::startup::IsProcessStartup` to determine whether
// this is the first profile that launched: The browser may be started
// without a startup window (`kNoStartupWindow`), or open the profile
// picker, which means that `chrome::startup::IsProcessStartup` will already
// be `kNo` when the first browser window is opened.
static bool infobars_shown = false;
if (infobars_shown)
return;
infobars_shown = true;
content::WebContents* web_contents =
browser->tab_strip_model()->GetActiveWebContents();
DCHECK(web_contents);
if (show_bad_flags_security_warnings)
chrome::ShowBadFlagsPrompt(web_contents);
infobars::ContentInfoBarManager* infobar_manager =
infobars::ContentInfoBarManager::FromWebContents(web_contents);
if (ObsoleteSystem::IsObsoleteNowOrSoon()) {
PrefService* local_state = g_browser_process->local_state();
if (!local_state ||
!local_state->GetBoolean(prefs::kSuppressUnsupportedOSWarning))
ObsoleteSystemInfoBarDelegate::Create(infobar_manager);
}
#if !BUILDFLAG(IS_CHROMEOS_ASH)
if (!is_web_app &&
!startup_command_line.HasSwitch(switches::kNoDefaultBrowserCheck)) {
// The default browser prompt should only be shown after the first run.
if (is_first_run == chrome::startup::IsFirstRun::kNo)
ShowDefaultBrowserPrompt(profile);
}
#endif
}
}

View file

@ -0,0 +1,311 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ui/ui_features.h"
#include "base/feature_list.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "ui_features.h"
namespace features {
// Enables the tab dragging fallback when full window dragging is not supported
// by the platform (e.g. Wayland). See https://crbug.com/896640
const base::Feature kAllowWindowDragUsingSystemDragDrop{
"AllowWindowDragUsingSystemDragDrop", base::FEATURE_ENABLED_BY_DEFAULT};
// Enables Chrome Labs menu in the toolbar. See https://crbug.com/1145666
const base::Feature kChromeLabs{"ChromeLabs",
base::FEATURE_ENABLED_BY_DEFAULT};
#if BUILDFLAG(GOOGLE_CHROME_BRANDING)
// Enables "Tips for Chrome" in Main Chrome Menu | Help.
const base::Feature kChromeTipsInMainMenu{"ChromeTipsInMainMenu",
base::FEATURE_DISABLED_BY_DEFAULT};
// Enables "Tips for Chrome" in Main Chrome Menu | Help.
const base::Feature kChromeTipsInMainMenuNewBadge{
"ChromeTipsInMainMenuNewBadge", base::FEATURE_DISABLED_BY_DEFAULT};
#endif
// Enables "Chrome What's New" UI.
const base::Feature kChromeWhatsNewUI {
"ChromeWhatsNewUI",
#if BUILDFLAG(GOOGLE_CHROME_BRANDING) && !defined(ANDROID) && \
!BUILDFLAG(IS_CHROMEOS_LACROS) && !BUILDFLAG(IS_CHROMEOS_ASH)
base::FEATURE_ENABLED_BY_DEFAULT
#else
base::FEATURE_DISABLED_BY_DEFAULT
#endif
};
#if BUILDFLAG(GOOGLE_CHROME_BRANDING)
// Enables "new" badge for "Chrome What's New" in Main Chrome Menu | Help.
const base::Feature kChromeWhatsNewInMainMenuNewBadge{
"ChromeWhatsNewInMainMenuNewBadge", base::FEATURE_DISABLED_BY_DEFAULT};
#endif
#if !defined(ANDROID)
// Enables "Access Code Cast" UI.
const base::Feature kAccessCodeCastUI{"AccessCodeCastUI",
base::FEATURE_ENABLED_BY_DEFAULT};
#endif
// Enables displaying the submenu to open a link with a different profile
// even if there is no other profile opened in a separate window
const base::Feature kDisplayOpenLinkAsProfile{
"DisplayOpenLinkAsProfile", base::FEATURE_DISABLED_BY_DEFAULT};
// Enables showing the EV certificate details in the Page Info bubble.
const base::Feature kEvDetailsInPageInfo{"EvDetailsInPageInfo",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables the reauth flow for authenticated profiles with invalid credentials
// when the force sign-in policy is enabled.
const base::Feature kForceSignInReauth{"ForceSignInReauth",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables a more prominent active tab title in dark mode to aid with
// accessibility.
const base::Feature kProminentDarkModeActiveTabTitle{
"ProminentDarkModeActiveTabTitle", base::FEATURE_ENABLED_BY_DEFAULT};
// Enables the QuickCommands UI surface. See https://crbug.com/1014639
const base::Feature kQuickCommands{"QuickCommands",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables the side search feature for Google Search. Presents recent Google
// search results in a browser side panel.
#if BUILDFLAG(IS_CHROMEOS_ASH)
// Enable by default as the ChromeOS iteration of Side Search has launched (See
// crbug.com/1242730).
const base::Feature kSideSearch{"SideSearch", base::FEATURE_ENABLED_BY_DEFAULT};
#else
// Disable by default on remaining desktop platforms until desktop UX has
// launched (See crbug.com/1279696).
const base::Feature kSideSearch{"SideSearch",
base::FEATURE_ENABLED_BY_DEFAULT};
#endif // BUILDFLAG(IS_CHROMEOS_ASH)
const base::Feature kSideSearchFeedback{"SideSearchFeedback",
base::FEATURE_DISABLED_BY_DEFAULT};
// Controls whether the Side Search feature is configured to support any
// participating Chrome search engine. This should always be enabled with
// kSideSearch on non-ChromeOS platforms.
const base::Feature kSideSearchDSESupport{"SideSearchDSESupport",
base::FEATURE_ENABLED_BY_DEFAULT};
// Controls whether the side search icon animates-in its label when the side
// panel is made available for the active tab.
const base::Feature kSideSearchPageActionLabelAnimation{
"SideSearchPageActionLabelAnimation", base::FEATURE_ENABLED_BY_DEFAULT};
// Controls the frequency that the Side Search page action's label is shown. If
// enabled the label text is shown one per window.
const base::FeatureParam<kSideSearchLabelAnimationTypeOption>::Option
kSideSearchPageActionLabelAnimationTypeParamOptions[] = {
{kSideSearchLabelAnimationTypeOption::kProfile, "Profile"},
{kSideSearchLabelAnimationTypeOption::kWindow, "Window"},
{kSideSearchLabelAnimationTypeOption::kTab, "Tab"}};
const base::FeatureParam<kSideSearchLabelAnimationTypeOption>
kSideSearchPageActionLabelAnimationType{
&kSideSearchPageActionLabelAnimation,
"SideSearchPageActionLabelAnimationType",
kSideSearchLabelAnimationTypeOption::kWindow,
&kSideSearchPageActionLabelAnimationTypeParamOptions};
const base::FeatureParam<int> kSideSearchPageActionLabelAnimationMaxCount{
&kSideSearchPageActionLabelAnimation,
"SideSearchPageActionLabelAnimationMaxCount", 1};
// Whether to clobber all side search side panels in the current browser window
// or only the side search in the current tab before read later or lens side
// panel is open.
const base::Feature kClobberAllSideSearchSidePanels{
"ClobberAllSideSearchSidePanels", base::FEATURE_ENABLED_BY_DEFAULT};
// Adds improved support for handling multiple contextual and global RHS browser
// side panels. Designed specifically to handle the interim state before the v2
// side panel project launches.
const base::Feature kSidePanelImprovedClobbering{
"SidePanelImprovedClobbering", base::FEATURE_DISABLED_BY_DEFAULT};
const base::Feature kSidePanelJourneys{"SidePanelJourneys",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables tabs to scroll in the tabstrip. https://crbug.com/951078
const base::Feature kScrollableTabStrip{"ScrollableTabStrip",
base::FEATURE_DISABLED_BY_DEFAULT};
const char kMinimumTabWidthFeatureParameterName[] = "minTabWidth";
// Directly controls the "new" badge (as opposed to old "master switch"; see
// https://crbug.com/1169907 for master switch deprecation and
// https://crbug.com/968587 for the feature itself)
// https://crbug.com/1173792
const base::Feature kTabGroupsNewBadgePromo{"TabGroupsNewBadgePromo",
base::FEATURE_DISABLED_BY_DEFAULT};
// Enables users to explicitly save and recall tab groups.
// https://crbug.com/1223929
const base::Feature kTabGroupsSave{"TabGroupsSave",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables preview images in tab-hover cards.
// https://crbug.com/928954
const base::Feature kTabHoverCardImages{"TabHoverCardImages",
base::FEATURE_ENABLED_BY_DEFAULT};
const char kTabHoverCardImagesNotReadyDelayParameterName[] =
"page_not_ready_delay";
const char kTabHoverCardImagesLoadingDelayParameterName[] =
"page_loading_delay";
const char kTabHoverCardImagesLoadedDelayParameterName[] = "page_loaded_delay";
const char kTabHoverCardImagesCrossfadePreviewAtParameterName[] =
"crossfade_preview_at";
const char kTabHoverCardAdditionalMaxWidthDelay[] =
"additional_max_width_delay";
const char kTabHoverCardAlternateFormat[] = "alternate_format";
// Enables tab outlines in additional situations for accessibility.
const base::Feature kTabOutlinesInLowContrastThemes{
"TabOutlinesInLowContrastThemes", base::FEATURE_ENABLED_BY_DEFAULT};
const base::Feature kTabSearchChevronIcon{"TabSearchChevronIcon",
base::FEATURE_ENABLED_BY_DEFAULT};
// Enables the tab search submit feedback button.
const base::Feature kTabSearchFeedback{"TabSearchFeedback",
base::FEATURE_DISABLED_BY_DEFAULT};
// Controls whether or not to use fuzzy search for tab search.
const base::Feature kTabSearchFuzzySearch{"TabSearchFuzzySearch",
base::FEATURE_DISABLED_BY_DEFAULT};
const char kTabSearchSearchThresholdName[] = "TabSearchSearchThreshold";
const base::FeatureParam<bool> kTabSearchSearchIgnoreLocation{
&kTabSearchFuzzySearch, "TabSearchSearchIgnoreLocation", false};
const base::Feature kTabSearchMediaTabs{"TabSearchMediaTabs",
base::FEATURE_ENABLED_BY_DEFAULT};
// If this feature parameter is enabled, show media tabs in both "Audio & Video"
// section and "Open Tabs" section.
const char kTabSearchAlsoShowMediaTabsinOpenTabsSectionParameterName[] =
"Also show Media Tabs in Open Tabs Section";
const base::FeatureParam<int> kTabSearchSearchDistance{
&kTabSearchFuzzySearch, "TabSearchSearchDistance", 200};
const base::FeatureParam<double> kTabSearchSearchThreshold{
&kTabSearchFuzzySearch, kTabSearchSearchThresholdName, 0.6};
const base::FeatureParam<double> kTabSearchTitleWeight{
&kTabSearchFuzzySearch, "TabSearchTitleWeight", 2.0};
const base::FeatureParam<double> kTabSearchHostnameWeight{
&kTabSearchFuzzySearch, "TabSearchHostnameWeight", 1.0};
const base::FeatureParam<double> kTabSearchGroupTitleWeight{
&kTabSearchFuzzySearch, "TabSearchGroupTitleWeight", 1.5};
const base::FeatureParam<bool> kTabSearchMoveActiveTabToBottom{
&kTabSearchFuzzySearch, "TabSearchMoveActiveTabToBottom", true};
// Controls feature parameters for Tab Search's `Recently Closed` entries.
const base::Feature kTabSearchRecentlyClosed{"TabSearchRecentlyClosed",
base::FEATURE_ENABLED_BY_DEFAULT};
const base::FeatureParam<int> kTabSearchRecentlyClosedDefaultItemDisplayCount{
&kTabSearchRecentlyClosed, "TabSearchRecentlyClosedDefaultItemDisplayCount",
8};
const base::FeatureParam<int> kTabSearchRecentlyClosedTabCountThreshold{
&kTabSearchRecentlyClosed, "TabSearchRecentlyClosedTabCountThreshold", 100};
const base::Feature kTabSearchUseMetricsReporter{
"TabSearchUseMetricsReporter", base::FEATURE_DISABLED_BY_DEFAULT};
const base::Feature kToolbarUseHardwareBitmapDraw{
"ToolbarUseHardwareBitmapDraw", base::FEATURE_DISABLED_BY_DEFAULT};
const base::Feature kUnifiedSidePanel{"UnifiedSidePanel",
base::FEATURE_DISABLED_BY_DEFAULT};
// This enables enables persistence of a WebContents in a 1-to-1 association
// with the current Profile for WebUI bubbles. See https://crbug.com/1177048.
const base::Feature kWebUIBubblePerProfilePersistence{
"WebUIBubblePerProfilePersistence", base::FEATURE_DISABLED_BY_DEFAULT};
// Enables a web-based tab strip. See https://crbug.com/989131. Note this
// feature only works when the ENABLE_WEBUI_TAB_STRIP buildflag is enabled.
const base::Feature kWebUITabStrip {
"WebUITabStrip",
#if BUILDFLAG(IS_CHROMEOS)
base::FEATURE_ENABLED_BY_DEFAULT
};
#else
base::FEATURE_ENABLED_BY_DEFAULT
};
#endif
// The default value of this flag is aligned with platform behavior to handle
// context menu with touch.
// TODO(crbug.com/1257626): Enable this flag for all platforms after launch.
const base::Feature kWebUITabStripContextMenuAfterTap {
"WebUITabStripContextMenuAfterTap",
#if BUILDFLAG(IS_CHROMEOS_ASH)
base::FEATURE_DISABLED_BY_DEFAULT
#else
base::FEATURE_ENABLED_BY_DEFAULT
#endif
};
#if BUILDFLAG(IS_CHROMEOS)
const base::Feature kChromeOSTabSearchCaptionButton{
"ChromeOSTabSearchCaptionButton", base::FEATURE_ENABLED_BY_DEFAULT};
#endif
#if BUILDFLAG(IS_MAC)
// Enabled an experiment which increases the prominence to grant MacOS system
// location permission to Chrome when location permissions have already been
// approved. https://crbug.com/1211052
const base::Feature kLocationPermissionsExperiment{
"LocationPermissionsExperiment", base::FEATURE_DISABLED_BY_DEFAULT};
constexpr base::FeatureParam<int>
kLocationPermissionsExperimentBubblePromptLimit{
&kLocationPermissionsExperiment, "bubble_prompt_count", 3};
constexpr base::FeatureParam<int>
kLocationPermissionsExperimentLabelPromptLimit{
&kLocationPermissionsExperiment, "label_prompt_count", 5};
const base::Feature kViewsFirstRunDialog{"ViewsFirstRunDialog",
base::FEATURE_DISABLED_BY_DEFAULT};
const base::Feature kViewsTaskManager{"ViewsTaskManager",
base::FEATURE_DISABLED_BY_DEFAULT};
const base::Feature kViewsJSAppModalDialog{"ViewsJSAppModalDialog",
base::FEATURE_DISABLED_BY_DEFAULT};
int GetLocationPermissionsExperimentBubblePromptLimit() {
return kLocationPermissionsExperimentBubblePromptLimit.Get();
}
int GetLocationPermissionsExperimentLabelPromptLimit() {
return kLocationPermissionsExperimentLabelPromptLimit.Get();
}
#endif
#if BUILDFLAG(IS_WIN)
// Moves the Tab Search button into the browser frame's caption button area on
// Windows 10 (crbug.com/1223847).
const base::Feature kWin10TabSearchCaptionButton{
"Win10TabSearchCaptionButton", base::FEATURE_ENABLED_BY_DEFAULT};
#endif
} // namespace features

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,231 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ui/views/toolbar/reload_button.h"
#include <stddef.h>
#include "base/strings/utf_string_conversions.h"
#include "build/build_config.h"
#include "chrome/app/chrome_command_ids.h"
#include "chrome/app/vector_icons/vector_icons.h"
#include "chrome/browser/command_updater.h"
#include "chrome/browser/external_protocol/external_protocol_handler.h"
#include "chrome/browser/themes/theme_properties.h"
#include "chrome/browser/ui/view_ids.h"
#include "chrome/grit/generated_resources.h"
#include "components/vector_icons/vector_icons.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/metadata/metadata_impl_macros.h"
#include "ui/base/models/simple_menu_model.h"
#include "ui/base/pointer/touch_ui_controller.h"
#include "ui/base/theme_provider.h"
#include "ui/base/window_open_disposition.h"
#include "ui/gfx/color_palette.h"
#include "ui/gfx/paint_vector_icon.h"
#include "ui/views/metrics.h"
#include "ui/views/widget/widget.h"
// ReloadButton ---------------------------------------------------------------
ReloadButton::ReloadButton(CommandUpdater* command_updater)
: ToolbarButton(base::BindRepeating(&ReloadButton::ButtonPressed,
base::Unretained(this)),
CreateMenuModel(),
nullptr),
command_updater_(command_updater),
double_click_timer_delay_(
base::Milliseconds(views::GetDoubleClickInterval())),
mode_switch_timer_delay_(base::Milliseconds(1350)) {
SetVisibleMode(Mode::kReload);
SetTriggerableEventFlags(ui::EF_LEFT_MOUSE_BUTTON |
ui::EF_MIDDLE_MOUSE_BUTTON);
SetAccessibleName(l10n_util::GetStringUTF16(IDS_ACCNAME_RELOAD));
SetID(VIEW_ID_RELOAD_BUTTON);
}
ReloadButton::~ReloadButton() {}
void ReloadButton::ChangeMode(Mode mode, bool force) {
intended_mode_ = mode;
// If the change is forced, or the user isn't hovering the icon, or it's
// safe to change it to the other image type, make the change immediately;
// otherwise we'll let it happen later.
if (force || (!IsMouseHovered() && !testing_mouse_hovered_) ||
((mode == Mode::kStop) ? !double_click_timer_.IsRunning()
: (visible_mode_ != Mode::kStop))) {
double_click_timer_.Stop();
mode_switch_timer_.Stop();
SetVisibleMode(mode);
SetEnabled(true);
// We want to disable the button if we're preventing a change from stop to
// reload due to hovering, but not if we're preventing a change from
// reload to stop due to the double-click timer running. (Disabled reload
// state is only applicable when instant extended API is enabled and mode
// is NTP, which is handled just above.)
} else if (visible_mode_ != Mode::kReload) {
SetEnabled(false);
// Go ahead and change to reload after a bit, which allows repeated
// reloads without moving the mouse.
if (!mode_switch_timer_.IsRunning()) {
mode_switch_timer_.Start(FROM_HERE, mode_switch_timer_delay_, this,
&ReloadButton::OnStopToReloadTimer);
}
}
}
bool ReloadButton::GetMenuEnabled() const {
return menu_enabled_;
}
void ReloadButton::SetMenuEnabled(bool enable) {
menu_enabled_ = true;
}
void ReloadButton::OnMouseExited(const ui::MouseEvent& event) {
ToolbarButton::OnMouseExited(event);
if (!IsMenuShowing())
ChangeMode(intended_mode_, true);
}
std::u16string ReloadButton::GetTooltipText(const gfx::Point& p) const {
int reload_tooltip = menu_enabled_ ?
IDS_TOOLTIP_RELOAD_WITH_MENU : IDS_TOOLTIP_RELOAD;
return l10n_util::GetStringUTF16(
visible_mode_ == Mode::kReload ? reload_tooltip : IDS_TOOLTIP_STOP);
}
void ReloadButton::GetAccessibleNodeData(ui::AXNodeData* node_data) {
if (menu_enabled_)
ToolbarButton::GetAccessibleNodeData(node_data);
else
Button::GetAccessibleNodeData(node_data);
}
bool ReloadButton::ShouldShowMenu() {
return menu_enabled_ && (visible_mode_ == Mode::kReload);
}
void ReloadButton::ShowDropDownMenu(ui::MenuSourceType source_type) {
ToolbarButton::ShowDropDownMenu(source_type); // Blocks.
ChangeMode(intended_mode_, true);
}
bool ReloadButton::IsCommandIdChecked(int command_id) const {
return false;
}
bool ReloadButton::IsCommandIdEnabled(int command_id) const {
return true;
}
bool ReloadButton::IsCommandIdVisible(int command_id) const {
return true;
}
bool ReloadButton::GetAcceleratorForCommandId(
int command_id,
ui::Accelerator* accelerator) const {
return GetWidget()->GetAccelerator(command_id, accelerator);
}
void ReloadButton::ExecuteCommand(int command_id, int event_flags) {
ExecuteBrowserCommand(command_id, event_flags);
}
std::unique_ptr<ui::SimpleMenuModel> ReloadButton::CreateMenuModel() {
auto menu_model = std::make_unique<ui::SimpleMenuModel>(this);
menu_model->AddItemWithStringId(IDC_RELOAD,
IDS_RELOAD_MENU_NORMAL_RELOAD_ITEM);
menu_model->AddItemWithStringId(IDC_RELOAD_BYPASSING_CACHE,
IDS_RELOAD_MENU_HARD_RELOAD_ITEM);
menu_model->AddItemWithStringId(IDC_RELOAD_CLEARING_CACHE,
IDS_RELOAD_MENU_EMPTY_AND_HARD_RELOAD_ITEM);
return menu_model;
}
void ReloadButton::SetVisibleMode(Mode mode) {
visible_mode_ = mode;
switch (mode) {
case Mode::kReload:
SetVectorIcons(vector_icons::kReloadIcon, kReloadTouchIcon);
break;
case Mode::kStop:
SetVectorIcons(kNavigateStopIcon, kNavigateStopTouchIcon);
break;
}
}
void ReloadButton::ButtonPressed(const ui::Event& event) {
// This is called in order to signal that external protocol dialogs are
// allowed to show due to a user action, which are likely to happen on the
// next page load after the reload button is clicked.
// Ideally, the browser UI's event system would notify ExternalProtocolHandler
// that a user action occurred and we are OK to open the dialog, but for some
// reason that isn't happening every time the reload button is clicked. See
// http://crbug.com/1206456
ExternalProtocolHandler::PermitLaunchUrl();
ClearPendingMenu();
if (visible_mode_ == Mode::kStop) {
if (command_updater_) {
command_updater_->ExecuteCommandWithDisposition(
IDC_STOP, WindowOpenDisposition::CURRENT_TAB);
}
// The user has clicked, so we can feel free to update the button, even if
// the mouse is still hovering.
ChangeMode(Mode::kReload, true);
return;
}
if (!double_click_timer_.IsRunning()) {
// Shift-clicking or ctrl-clicking the reload button means we should ignore
// any cached content.
int command;
int flags = event.flags();
if (event.IsShiftDown() || event.IsControlDown()) {
command = IDC_RELOAD_BYPASSING_CACHE;
// Mask off Shift and Control so they don't affect the disposition below.
flags &= ~(ui::EF_SHIFT_DOWN | ui::EF_CONTROL_DOWN);
} else {
command = IDC_RELOAD;
}
// Start a timer - while this timer is running, the reload button cannot be
// changed to a stop button. We do not set |intended_mode_| to Mode::kStop
// here as the browser will do that when it actually starts loading (which
// may happen synchronously, thus the need to do this before telling the
// browser to execute the reload command).
double_click_timer_.Start(FROM_HERE, double_click_timer_delay_, this,
&ReloadButton::OnDoubleClickTimer);
ExecuteBrowserCommand(command, flags);
++testing_reload_count_;
}
}
void ReloadButton::ExecuteBrowserCommand(int command, int event_flags) {
if (!command_updater_)
return;
command_updater_->ExecuteCommandWithDisposition(
command, ui::DispositionFromEventFlags(event_flags));
}
void ReloadButton::OnDoubleClickTimer() {
if (!IsMenuShowing())
ChangeMode(intended_mode_, false);
}
void ReloadButton::OnStopToReloadTimer() {
DCHECK(!IsMenuShowing());
ChangeMode(intended_mode_, true);
}
BEGIN_METADATA(ReloadButton, ToolbarButton)
ADD_PROPERTY_METADATA(bool, MenuEnabled)
END_METADATA

View file

@ -0,0 +1,796 @@
// Copyright (c) 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/browser/ui/webui/about_ui.h"
#include <stddef.h>
#include <stdint.h>
#include <algorithm>
#include <memory>
#include <string>
#include <utility>
#include <vector>
#include "base/bind.h"
#include "base/callback.h"
#include "base/callback_helpers.h"
#include "base/command_line.h"
#include "base/files/file_path.h"
#include "base/files/file_util.h"
#include "base/format_macros.h"
#include "base/memory/ref_counted_memory.h"
#include "base/strings/escape.h"
#include "base/strings/string_split.h"
#include "base/strings/string_util.h"
#include "base/strings/stringprintf.h"
#include "base/strings/utf_string_conversions.h"
#include "base/task/thread_pool.h"
#include "base/threading/scoped_blocking_call.h"
#include "base/threading/thread.h"
#include "base/values.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "chrome/browser/about_flags.h"
#include "chrome/browser/ash/borealis/borealis_credits.h"
#include "chrome/browser/browser_process.h"
#include "chrome/browser/profiles/profile.h"
#include "chrome/browser/profiles/profile_manager.h"
#include "chrome/common/chrome_paths.h"
#include "chrome/common/url_constants.h"
#include "chrome/grit/browser_resources.h"
#include "chrome/grit/chromium_strings.h"
#include "chrome/grit/generated_resources.h"
#include "components/about_ui/credit_utils.h"
#include "components/grit/components_resources.h"
#include "components/strings/grit/components_locale_settings.h"
#include "components/strings/grit/components_strings.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/url_data_source.h"
#include "content/public/browser/web_contents.h"
#include "net/base/filename_util.h"
#include "ui/base/l10n/l10n_util.h"
#include "ui/base/resource/resource_bundle.h"
#include "ui/base/webui/web_ui_util.h"
#include "url/gurl.h"
#if !BUILDFLAG(IS_ANDROID)
#include "chrome/browser/ui/webui/theme_source.h"
#endif
#if BUILDFLAG(IS_CHROMEOS_ASH)
#include <map>
#include "base/base64.h"
#include "base/cxx17_backports.h"
#include "base/strings/strcat.h"
#include "chrome/browser/ash/crosapi/browser_manager.h"
#include "chrome/browser/ash/crosapi/browser_util.h"
#include "chrome/browser/ash/crostini/crostini_features.h"
#include "chrome/browser/ash/crostini/crostini_manager.h"
#include "chrome/browser/ash/customization/customization_document.h"
#include "chrome/browser/ash/login/demo_mode/demo_setup_controller.h"
#include "chrome/browser/ash/login/wizard_controller.h"
#include "chrome/browser/browser_process_platform_part_ash.h"
#include "chrome/browser/component_updater/cros_component_manager.h"
#include "chrome/browser/ui/webui/chrome_web_ui_controller_factory.h"
#include "chrome/common/webui_url_constants.h"
#include "chromeos/system/statistics_provider.h"
#include "components/language/core/common/locale_util.h"
#include "third_party/cros_system_api/dbus/service_constants.h"
#endif
#if BUILDFLAG(IS_CHROMEOS_LACROS)
#include "chrome/browser/lacros/lacros_url_handling.h"
#endif // BUILDFLAG(IS_CHROMEOS_LACROS)
#if BUILDFLAG(IS_CHROMEOS)
#include "chrome/common/webui_url_constants.h"
#include "ui/base/l10n/l10n_util.h"
#endif // BUILDFLAG(IS_CHROMEOS)
using content::BrowserThread;
namespace {
constexpr char kCreditsJsPath[] = "credits.js";
constexpr char kCreditsCssPath[] = "credits.css";
constexpr char kStatsJsPath[] = "stats.js";
constexpr char kStringsJsPath[] = "strings.js";
#if BUILDFLAG(IS_CHROMEOS_ASH)
constexpr char kKeyboardUtilsPath[] = "keyboard_utils.js";
constexpr char kTerminaCreditsPath[] = "about_os_credits.html";
// APAC region name.
constexpr char kApac[] = "apac";
// EMEA region name.
constexpr char kEmea[] = "emea";
// EU region name.
constexpr char kEu[] = "eu";
// List of countries that belong to APAC.
const char* const kApacCountries[] = {"au", "bd", "cn", "hk", "id", "in", "jp",
"kh", "la", "lk", "mm", "mn", "my", "nz",
"np", "ph", "sg", "th", "tw", "vn"};
// List of countries that belong to EMEA.
const char* const kEmeaCountries[] = {"na", "za", "am", "az", "ch", "eg", "ge",
"il", "is", "ke", "kg", "li", "mk", "no",
"rs", "ru", "tr", "tz", "ua", "ug", "za"};
// List of countries that belong to EU.
const char* const kEuCountries[] = {
"at", "be", "bg", "cz", "dk", "es", "fi", "fr", "gb", "gr", "hr", "hu",
"ie", "it", "lt", "lu", "lv", "nl", "pl", "pt", "ro", "se", "si", "sk"};
// Maps country to one of 3 regions: APAC, EMEA, EU.
typedef std::map<std::string, std::string> CountryRegionMap;
// Returns country to region map with EU, EMEA and APAC countries.
CountryRegionMap CreateCountryRegionMap() {
CountryRegionMap region_map;
for (size_t i = 0; i < std::size(kApacCountries); ++i) {
region_map.emplace(kApacCountries[i], kApac);
}
for (size_t i = 0; i < std::size(kEmeaCountries); ++i) {
region_map.emplace(kEmeaCountries[i], kEmea);
}
for (size_t i = 0; i < std::size(kEuCountries); ++i) {
region_map.emplace(kEuCountries[i], kEu);
}
return region_map;
}
// Reads device region from VPD. Returns "us" in case of read or parsing errors.
std::string ReadDeviceRegionFromVpd() {
std::string region = "us";
chromeos::system::StatisticsProvider* provider =
chromeos::system::StatisticsProvider::GetInstance();
bool region_found =
provider->GetMachineStatistic(chromeos::system::kRegionKey, &region);
if (region_found) {
// We only need the first part of the complex region codes like ca.ansi.
std::vector<std::string> region_pieces = base::SplitString(
region, ".", base::TRIM_WHITESPACE, base::SPLIT_WANT_NONEMPTY);
if (!region_pieces.empty())
region = region_pieces[0];
} else {
LOG(WARNING) << "Device region for Play Store ToS not found in VPD - "
"defaulting to US.";
}
return base::ToLowerASCII(region);
}
// Loads bundled terms of service contents (Eula, OEM Eula, Play Store Terms).
// The online version of terms is fetched in OOBE screen javascript. This is
// intentional because chrome://terms runs in a privileged webui context and
// should never load from untrusted places.
class ChromeOSTermsHandler
: public base::RefCountedThreadSafe<ChromeOSTermsHandler> {
public:
ChromeOSTermsHandler(const ChromeOSTermsHandler&) = delete;
ChromeOSTermsHandler& operator=(const ChromeOSTermsHandler&) = delete;
static void Start(const std::string& path,
content::URLDataSource::GotDataCallback callback) {
scoped_refptr<ChromeOSTermsHandler> handler(
new ChromeOSTermsHandler(path, std::move(callback)));
handler->StartOnUIThread();
}
private:
friend class base::RefCountedThreadSafe<ChromeOSTermsHandler>;
ChromeOSTermsHandler(const std::string& path,
content::URLDataSource::GotDataCallback callback)
: path_(path),
callback_(std::move(callback)),
// Previously we were using "initial locale" http://crbug.com/145142
locale_(g_browser_process->GetApplicationLocale()) {}
virtual ~ChromeOSTermsHandler() {}
void StartOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
if (path_ == chrome::kOemEulaURLPath) {
// Load local OEM EULA from the disk.
base::ThreadPool::PostTaskAndReply(
FROM_HERE, {base::MayBlock(), base::TaskPriority::USER_VISIBLE},
base::BindOnce(&ChromeOSTermsHandler::LoadOemEulaFileAsync, this),
base::BindOnce(&ChromeOSTermsHandler::ResponseOnUIThread, this));
} else if (path_ == chrome::kArcTermsURLPath) {
LOG(WARNING) << "Could not load offline Play Store ToS.";
} else if (path_ == chrome::kArcPrivacyPolicyURLPath) {
LOG(WARNING) << "Could not load offline Play Store privacy policy.";
} else {
NOTREACHED();
ResponseOnUIThread();
}
}
void LoadOemEulaFileAsync() {
base::ScopedBlockingCall scoped_blocking_call(
FROM_HERE, base::BlockingType::MAY_BLOCK);
const ash::StartupCustomizationDocument* customization =
ash::StartupCustomizationDocument::GetInstance();
if (!customization->IsReady())
return;
base::FilePath oem_eula_file_path;
if (net::FileURLToFilePath(GURL(customization->GetEULAPage(locale_)),
&oem_eula_file_path)) {
if (!base::ReadFileToString(oem_eula_file_path, &contents_)) {
contents_.clear();
}
}
}
std::vector<std::string> CreateArcLocaleLookupArray() {
// To get Play Store asset we look for the first locale match in the
// following order:
// * language and device region combination
// * default region (APAC, EMEA, EU)
// * en-US
// Note: AMERICAS region defaults to en-US and to simplify it is not
// included in the country region map.
std::vector<std::string> locale_lookup_array;
const std::string device_region = ReadDeviceRegionFromVpd();
locale_lookup_array.push_back(base::StrCat(
{base::ToLowerASCII(language::ExtractBaseLanguage(locale_)), "-",
device_region}));
const CountryRegionMap country_region_map = CreateCountryRegionMap();
const auto region = country_region_map.find(device_region);
if (region != country_region_map.end()) {
locale_lookup_array.push_back(region->second.c_str());
}
locale_lookup_array.push_back("en-us");
return locale_lookup_array;
}
void ResponseOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
// If we fail to load Chrome OS EULA from disk, load it from resources.
// Do nothing if OEM EULA or Play Store ToS load failed.
if (contents_.empty() && path_.empty()) {
contents_ =
ui::ResourceBundle::GetSharedInstance().LoadLocalizedResourceString(
IDS_TERMS_HTML);
}
std::move(callback_).Run(
base::RefCountedString::TakeString(std::move(contents_)));
}
// Path in the URL.
const std::string path_;
// Callback to run with the response.
content::URLDataSource::GotDataCallback callback_;
// Locale of the EULA.
const std::string locale_;
// EULA contents that was loaded from file.
std::string contents_;
};
class ChromeOSCreditsHandler
: public base::RefCountedThreadSafe<ChromeOSCreditsHandler> {
public:
ChromeOSCreditsHandler(const ChromeOSCreditsHandler&) = delete;
ChromeOSCreditsHandler& operator=(const ChromeOSCreditsHandler&) = delete;
static void Start(const std::string& path,
content::URLDataSource::GotDataCallback callback) {
scoped_refptr<ChromeOSCreditsHandler> handler(
new ChromeOSCreditsHandler(path, std::move(callback)));
handler->StartOnUIThread();
}
private:
friend class base::RefCountedThreadSafe<ChromeOSCreditsHandler>;
ChromeOSCreditsHandler(const std::string& path,
content::URLDataSource::GotDataCallback callback)
: path_(path), callback_(std::move(callback)) {}
virtual ~ChromeOSCreditsHandler() {}
void StartOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
if (path_ == kKeyboardUtilsPath) {
contents_ =
ui::ResourceBundle::GetSharedInstance().LoadDataResourceString(
IDR_KEYBOARD_UTILS_JS);
ResponseOnUIThread();
return;
}
// Load local Chrome OS credits from the disk.
base::ThreadPool::PostTaskAndReply(
FROM_HERE, {base::MayBlock(), base::TaskPriority::BEST_EFFORT},
base::BindOnce(&ChromeOSCreditsHandler::LoadCreditsFileAsync, this),
base::BindOnce(&ChromeOSCreditsHandler::ResponseOnUIThread, this));
}
void LoadCreditsFileAsync() {
base::FilePath credits_file_path(chrome::kChromeOSCreditsPath);
if (!base::ReadFileToString(credits_file_path, &contents_)) {
// File with credits not found, ResponseOnUIThread will load credits
// from resources if contents_ is empty.
contents_.clear();
}
}
void ResponseOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
// If we fail to load Chrome OS credits from disk, load it from resources.
if (contents_.empty() && path_ != kKeyboardUtilsPath) {
contents_ =
ui::ResourceBundle::GetSharedInstance().LoadDataResourceString(
IDR_OS_CREDITS_HTML);
}
std::move(callback_).Run(
base::RefCountedString::TakeString(std::move(contents_)));
}
// Path in the URL.
const std::string path_;
// Callback to run with the response.
content::URLDataSource::GotDataCallback callback_;
// Chrome OS credits contents that was loaded from file.
std::string contents_;
};
void OnBorealisCreditsLoaded(content::URLDataSource::GotDataCallback callback,
std::string credits_html) {
if (credits_html.empty()) {
credits_html = l10n_util::GetStringUTF8(IDS_BOREALIS_CREDITS_PLACEHOLDER);
}
std::move(callback).Run(
base::RefCountedString::TakeString(std::move(credits_html)));
}
void HandleBorealisCredits(Profile* profile,
content::URLDataSource::GotDataCallback callback) {
borealis::LoadBorealisCredits(
profile, base::BindOnce(&OnBorealisCreditsLoaded, std::move(callback)));
}
class CrostiniCreditsHandler
: public base::RefCountedThreadSafe<CrostiniCreditsHandler> {
public:
CrostiniCreditsHandler(const CrostiniCreditsHandler&) = delete;
CrostiniCreditsHandler& operator=(const CrostiniCreditsHandler&) = delete;
static void Start(Profile* profile,
const std::string& path,
content::URLDataSource::GotDataCallback callback) {
scoped_refptr<CrostiniCreditsHandler> handler(
new CrostiniCreditsHandler(profile, path, std::move(callback)));
handler->StartOnUIThread();
}
private:
friend class base::RefCountedThreadSafe<CrostiniCreditsHandler>;
CrostiniCreditsHandler(Profile* profile,
const std::string& path,
content::URLDataSource::GotDataCallback callback)
: path_(path), callback_(std::move(callback)), profile_(profile) {}
virtual ~CrostiniCreditsHandler() {}
void StartOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
if (path_ == kKeyboardUtilsPath) {
contents_ =
ui::ResourceBundle::GetSharedInstance().LoadDataResourceString(
IDR_KEYBOARD_UTILS_JS);
RespondOnUIThread();
return;
}
if (crostini::CrostiniFeatures::Get()->IsAllowedNow(profile_)) {
crostini::CrostiniManager::GetForProfile(profile_)->GetInstallLocation(
base::BindOnce(&CrostiniCreditsHandler::LoadCredits, this));
} else {
RespondWithPlaceholder();
}
}
void LoadCredits(base::FilePath path) {
if (path.empty()) {
RespondWithPlaceholder();
return;
}
// Load crostini credits from the disk.
base::ThreadPool::PostTaskAndReply(
FROM_HERE, {base::MayBlock(), base::TaskPriority::BEST_EFFORT},
base::BindOnce(&CrostiniCreditsHandler::LoadCrostiniCreditsFileAsync,
this, path.Append(kTerminaCreditsPath)),
base::BindOnce(&CrostiniCreditsHandler::RespondOnUIThread, this));
}
void LoadCrostiniCreditsFileAsync(base::FilePath credits_file_path) {
if (!base::ReadFileToString(credits_file_path, &contents_)) {
// File with credits not found, RespondOnUIThread will load a placeholder
// if contents_ is empty.
contents_.clear();
}
}
void RespondWithPlaceholder() {
contents_.clear();
RespondOnUIThread();
}
void RespondOnUIThread() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
// If we fail to load Linux credits from disk, use the placeholder.
if (contents_.empty() && path_ != kKeyboardUtilsPath) {
contents_ = l10n_util::GetStringUTF8(IDS_CROSTINI_CREDITS_PLACEHOLDER);
}
std::move(callback_).Run(
base::RefCountedString::TakeString(std::move(contents_)));
}
// Path in the URL.
const std::string path_;
// Callback to run with the response.
content::URLDataSource::GotDataCallback callback_;
// Linux credits contents that was loaded from file.
std::string contents_;
Profile* profile_;
};
#endif
} // namespace
// Individual about handlers ---------------------------------------------------
namespace about_ui {
void AppendHeader(std::string* output, const std::string& unescaped_title) {
output->append("<!DOCTYPE HTML>\n<html>\n<head>\n");
output->append("<meta charset='utf-8'>\n");
output->append("<meta name='color-scheme' content='light dark'>\n");
if (!unescaped_title.empty()) {
output->append("<title>");
output->append(base::EscapeForHTML(unescaped_title));
output->append("</title>\n");
}
}
#if BUILDFLAG(IS_CHROMEOS)
// This function returns true if Lacros is the primary browser - or if the
// calling browser is Lacros.
bool isLacrosPrimaryOrCurrentBrowser() {
#if BUILDFLAG(IS_CHROMEOS_ASH)
return crosapi::browser_util::IsLacrosPrimaryBrowser();
#else
return true;
#endif
}
void AppendBody(std::string* output) {
if (isLacrosPrimaryOrCurrentBrowser()) {
output->append(
"<link rel='stylesheet' href='chrome://resources/css/os_header.css'>\n"
"</head>\n<body>\n"
"<div class='os-link-container-container' id='os-link-container'>\n"
"<div class='os-link-container'>\n"
"<span class='os-link-icon'></span>\n"
"<span aria-hidden='true' id='os-link-desc'>" +
l10n_util::GetStringUTF8(IDS_ABOUT_OS_TEXT1_LABEL) +
"</span>\n"
"<a href='#' id='os-link-href' aria-describedby='os-link-desc'>" +
l10n_util::GetStringUTF8(IDS_ABOUT_OS_LINK) +
"</a>\n<span aria-hidden='true'>" +
l10n_util::GetStringUTF8(IDS_ABOUT_OS_TEXT2_LABEL) +
"</span>\n</div>\n</div>\n");
} else {
output->append("</head>\n<body>\n");
}
}
void AppendFooter(std::string* output) {
if (isLacrosPrimaryOrCurrentBrowser()) {
output->append(
"<script type='module' src='chrome://resources/js/os_about.js'>"
"</script>\n");
}
output->append("</body>\n</html>\n");
}
#else // BUILDFLAG(IS_CHROMEOS)
void AppendBody(std::string *output) {
output->append("</head>\n<body>\n");
}
void AppendFooter(std::string *output) {
output->append("</body>\n</html>\n");
}
#endif // BUILDFLAG(IS_CHROMEOS)
} // namespace about_ui
using about_ui::AppendHeader;
using about_ui::AppendBody;
using about_ui::AppendFooter;
namespace {
std::string ChromeURLs() {
std::string html;
AppendHeader(&html, "Thorium URLs");
AppendBody(&html);
html += "<h2>List of Thorium URLs</h2>\n<ul>\n";
std::vector<std::string> hosts(
chrome::kChromeHostURLs,
chrome::kChromeHostURLs + chrome::kNumberOfChromeHostURLs);
std::sort(hosts.begin(), hosts.end());
#if BUILDFLAG(IS_CHROMEOS_ASH)
const bool is_lacros_primary = about_ui::isLacrosPrimaryOrCurrentBrowser();
// If Lacros is active, the user can navigate by hand to os:// URL's but
// internally we will still navigate to chrome:// URL's. Note also that
// only a subset of URLs might be available in this mode - so we have to
// make sure that only allowed URLs are being presented.
if (is_lacros_primary) {
auto* WebUiControllerFactory = ChromeWebUIControllerFactory::GetInstance();
for (const std::string& host : hosts) {
// TODO(crbug/1271718): The refactor should make sure that the provided
// list can be shown as is without filtering.
if (WebUiControllerFactory->CanHandleUrl(GURL("os://" + host)) ||
WebUiControllerFactory->CanHandleUrl(GURL("chrome://" + host))) {
html +=
"<li><a href='chrome://" + host + "/'>os://" + host + "</a></li>\n";
}
}
} else {
#else
{
#endif // BUILDFLAG(IS_CHROMEOS_ASH)
for (const std::string& host : hosts) {
html += "<li><a href='chrome://" + host + "/'>chrome://" + host +
"</a></li>\n";
}
html +=
"</ul><a id=\"internals\"><h2>List of chrome://internals "
"pages</h2></a>\n<ul>\n";
std::vector<std::string> internals_paths(
chrome::kChromeInternalsPathURLs,
chrome::kChromeInternalsPathURLs +
chrome::kNumberOfChromeInternalsPathURLs);
std::sort(internals_paths.begin(), internals_paths.end());
for (const std::string& path : internals_paths) {
html += "<li><a href='chrome://internals/" + path +
"'>chrome://internals/" + path + "</a></li>\n";
}
}
html += "</ul>\n<h2>For Debugging</h2>\n"
"<p>The following pages are for debugging purposes only. Because they "
"crash or hang the renderer, they're not linked directly; you can type "
"them into the address bar if you need them.</p>\n<ul>";
#if BUILDFLAG(IS_CHROMEOS_ASH)
// If Lacros is active, the user can navigate by hand to os:// URL's but
// internally we will still navigate to chrome:// URL's. Note also that
// only a subset of URLs might be available in this mode - so we have to
// make sure that only allowed URLs are being presented.
if (is_lacros_primary) {
auto* WebUiControllerFactory = ChromeWebUIControllerFactory::GetInstance();
for (size_t i = 0; i < chrome::kNumberOfChromeDebugURLs; i++) {
// TODO(crbug/1271718): The refactor should make sure that the provided
// list can be shown as is without filtering.
const std::string host = GURL(chrome::kChromeDebugURLs[i]).host();
if (WebUiControllerFactory->CanHandleUrl(GURL("os://" + host)) ||
WebUiControllerFactory->CanHandleUrl(GURL("chrome://" + host))) {
html += "<li>os://" + host + "</li>\n";
}
}
} else {
#else
{
#endif // BUILDFLAG(IS_CHROMEOS_ASH)
for (size_t i = 0; i < chrome::kNumberOfChromeDebugURLs; i++)
html += "<li>" + std::string(chrome::kChromeDebugURLs[i]) + "</li>\n";
}
html += "</ul>\n";
AppendFooter(&html);
return html;
}
#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_OPENBSD)
std::string AboutLinuxProxyConfig() {
std::string data;
AppendHeader(&data,
l10n_util::GetStringUTF8(IDS_ABOUT_LINUX_PROXY_CONFIG_TITLE));
data.append("<style>body { max-width: 70ex; padding: 2ex 5ex; }</style>");
AppendBody(&data);
base::FilePath binary = base::CommandLine::ForCurrentProcess()->GetProgram();
data.append(
l10n_util::GetStringFUTF8(IDS_ABOUT_LINUX_PROXY_CONFIG_BODY,
l10n_util::GetStringUTF16(IDS_PRODUCT_NAME),
base::ASCIIToUTF16(binary.BaseName().value())));
AppendFooter(&data);
return data;
}
#endif
} // namespace
// AboutUIHTMLSource ----------------------------------------------------------
AboutUIHTMLSource::AboutUIHTMLSource(const std::string& source_name,
Profile* profile)
: source_name_(source_name),
profile_(profile) {}
AboutUIHTMLSource::~AboutUIHTMLSource() {}
std::string AboutUIHTMLSource::GetSource() {
return source_name_;
}
void AboutUIHTMLSource::StartDataRequest(
const GURL& url,
const content::WebContents::Getter& wc_getter,
content::URLDataSource::GotDataCallback callback) {
// TODO(crbug/1009127): Simplify usages of |path| since |url| is available.
const std::string path = content::URLDataSource::URLToRequestPath(url);
std::string response;
// Add your data source here, in alphabetical order.
if (source_name_ == chrome::kChromeUIChromeURLsHost) {
response = ChromeURLs();
} else if (source_name_ == chrome::kChromeUICreditsHost) {
int idr = IDR_ABOUT_UI_CREDITS_HTML;
if (path == kCreditsJsPath)
idr = IDR_ABOUT_UI_CREDITS_JS;
else if (path == kCreditsCssPath)
idr = IDR_ABOUT_UI_CREDITS_CSS;
#if BUILDFLAG(IS_CHROMEOS_ASH)
else if (path == kKeyboardUtilsPath)
idr = IDR_KEYBOARD_UTILS_JS;
#endif
if (idr == IDR_ABOUT_UI_CREDITS_HTML) {
response = about_ui::GetCredits(true /*include_scripts*/);
} else {
response =
ui::ResourceBundle::GetSharedInstance().LoadDataResourceString(idr);
}
#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_OPENBSD)
} else if (source_name_ == chrome::kChromeUILinuxProxyConfigHost) {
response = AboutLinuxProxyConfig();
#endif
#if BUILDFLAG(IS_CHROMEOS_ASH)
} else if (source_name_ == chrome::kChromeUIOSCreditsHost) {
ChromeOSCreditsHandler::Start(path, std::move(callback));
return;
} else if (source_name_ == chrome::kChromeUICrostiniCreditsHost) {
CrostiniCreditsHandler::Start(profile(), path, std::move(callback));
return;
} else if (source_name_ == chrome::kChromeUIBorealisCreditsHost) {
HandleBorealisCredits(profile(), std::move(callback));
return;
#endif
#if !BUILDFLAG(IS_ANDROID)
} else if (source_name_ == chrome::kChromeUITermsHost) {
#if BUILDFLAG(IS_CHROMEOS_ASH)
if (!path.empty()) {
ChromeOSTermsHandler::Start(path, std::move(callback));
return;
}
#endif
response =
ui::ResourceBundle::GetSharedInstance().LoadLocalizedResourceString(
IDS_TERMS_HTML);
#endif
}
FinishDataRequest(response, std::move(callback));
}
void AboutUIHTMLSource::FinishDataRequest(
const std::string& html,
content::URLDataSource::GotDataCallback callback) {
std::string html_copy(html);
std::move(callback).Run(
base::RefCountedString::TakeString(std::move(html_copy)));
}
std::string AboutUIHTMLSource::GetMimeType(const std::string& path) {
if (path == kCreditsJsPath ||
#if BUILDFLAG(IS_CHROMEOS_ASH)
path == kKeyboardUtilsPath ||
#endif
path == kStatsJsPath || path == kStringsJsPath) {
return "application/javascript";
}
if (path == kCreditsCssPath) {
return "text/css";
}
return "text/html";
}
bool AboutUIHTMLSource::ShouldAddContentSecurityPolicy() {
#if BUILDFLAG(IS_CHROMEOS_ASH)
if (source_name_ == chrome::kChromeUIOSCreditsHost ||
source_name_ == chrome::kChromeUICrostiniCreditsHost ||
source_name_ == chrome::kChromeUIBorealisCreditsHost) {
return false;
}
#endif
return content::URLDataSource::ShouldAddContentSecurityPolicy();
}
std::string AboutUIHTMLSource::GetAccessControlAllowOriginForOrigin(
const std::string& origin) {
#if BUILDFLAG(IS_CHROMEOS_ASH)
// Allow chrome://oobe to load chrome://terms via XHR.
if (source_name_ == chrome::kChromeUITermsHost &&
base::StartsWith(chrome::kChromeUIOobeURL, origin,
base::CompareCase::SENSITIVE)) {
return origin;
}
#endif
return content::URLDataSource::GetAccessControlAllowOriginForOrigin(origin);
}
AboutUI::AboutUI(content::WebUI* web_ui, const std::string& name)
: WebUIController(web_ui) {
Profile* profile = Profile::FromWebUI(web_ui);
#if !BUILDFLAG(IS_ANDROID)
// Set up the chrome://theme/ source.
content::URLDataSource::Add(profile, std::make_unique<ThemeSource>(profile));
#endif
content::URLDataSource::Add(
profile, std::make_unique<AboutUIHTMLSource>(name, profile));
}
#if BUILDFLAG(IS_CHROMEOS)
bool AboutUI::OverrideHandleWebUIMessage(const GURL& source_url,
const std::string& message,
const base::Value::List& args) {
if (message != "crosUrlAboutRedirect")
return false;
#if BUILDFLAG(IS_CHROMEOS_LACROS)
lacros_url_handling::NavigateInAsh(GURL(chrome::kOsUIAboutURL));
#else
// Note: This will only be called by the UI when Lacros is available.
DCHECK(crosapi::BrowserManager::Get());
crosapi::BrowserManager::Get()->SwitchToTab(
GURL(chrome::kChromeUIAboutURL),
/*path_behavior=*/NavigateParams::RESPECT);
#endif
return true;
}
#endif // BUILDFLAG(IS_CHROMEOS)

Binary file not shown.

After

Width:  |  Height:  |  Size: 40 KiB

View file

@ -0,0 +1,68 @@
// Copyright 2022 The Chromium Authors and Alex313031. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include <windows.h>
#include "base/command_line.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/path_service.h"
#include "base/process/launch.h"
namespace {
constexpr base::FilePath::CharType kChromeExecutable[] =
FILE_PATH_LITERAL("thorium.exe");
constexpr base::FilePath::CharType kChromeProxyExecutable[] =
FILE_PATH_LITERAL("chrome_proxy.exe");
} // namespace
// This binary is a workaround for Windows 10 start menu pinning icon bug:
// https://crbug.com/732357.
//
// When a shortcut is pinned in the Windows 10 start menu Windows will follow
// the shortcut, find the target executable, look for a <target>.manifest file
// in the same directory and use the icon specified in there for the start menu
// pin. Because bookmark app shortcuts are shortcuts to Chrome (plus a few
// command line parameters) Windows ends up using the Chrome icon specified in
// chrome.VisualElementsManifest.xml instead of the site's icon stored inside
// the shortcut.
//
// The chrome_proxy.exe binary workaround "fixes" this by having bookmark app
// shortcuts target chrome_proxy.exe instead of chrome.exe such that Windows
// won't find a manifest and falls back to using the shortcut's icons as
// originally intended.
int WINAPI wWinMain(HINSTANCE instance,
HINSTANCE prev_instance,
wchar_t* /*command_line*/,
int show_command) {
base::CommandLine::Init(0, nullptr);
logging::LoggingSettings logging_settings;
logging_settings.logging_dest =
logging::LOG_TO_SYSTEM_DEBUG_LOG | logging::LOG_TO_STDERR;
logging::InitLogging(logging_settings);
base::FilePath chrome_dir;
CHECK(base::PathService::Get(base::DIR_EXE, &chrome_dir));
base::CommandLine chrome_command_line(chrome_dir.Append(kChromeExecutable));
// Forward all command line arguments.
const std::vector<std::wstring>& argv =
base::CommandLine::ForCurrentProcess()->argv();
// The first one is always the current executable path.
CHECK(argv.size() > 0);
CHECK_EQ(base::FilePath(argv[0]).BaseName().value(), kChromeProxyExecutable);
for (size_t i = 1; i < argv.size(); ++i)
chrome_command_line.AppendArgNative(argv[i]);
base::LaunchOptions launch_options;
launch_options.current_directory = chrome_dir;
launch_options.grant_foreground_privilege = true;
CHECK(base::LaunchProcess(chrome_command_line, launch_options).IsValid());
return 0;
}