CINXE.COM

Building native software

<!DOCTYPE html> <html lang=""> <head> <meta charset="utf-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="generator" content="Asciidoctor 2.0.23"> <title>Building native software</title> <style> /* * Copyright 2018 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /* Custom Admonition Blocks */ body { --gradle-blue: #209BC4; --gradle-bg-dark: #010002; --gradle-bg-gray: #F8F8F8; --gradle-bg-white: #FFFFFF; --gradle-blue: #209BC4; --gradle-blue-lite: #4DC9C0; --gradle-blue-dark: #1b3262; --gradle-blue-darker: #19274f; --button-gradient-angle: 160deg; --caution-color: #e40046; --caution-on-color: #fff; --important-color: #802392; --important-on-color: #fff; --note-color: #2d7dd2; --note-on-color: #fff; --tip-color: #43b929; --tip-on-color: #fff; --warning-color: #f70; --warning-on-color: #fff; --admonition-background: #fafafa; --doc-icon-filter: invert(14.5%); --rem-base: 18; --black-color: #000; --white-color: #fff; --text-color: #02303A; --title-color: #02303A; --header-color: rgba(0, 0, 0, 0.85); --footer-color: #fff; --footer-other-text-color: #02303; --footer-form-color: #1BA8CB; --code-color: #f7f7f8; --code-text-color: rgba(0, 0, 0, 0.9); --code-link-color: #021274; --num-color: rgba(0, 0, 0, 0.8); --nav-color: #f8f8f7; --table-color: #f7f8f7; --box-shadow-color: rgba(0, 0, 0, .15); --top-header-color: #fff; --footer-white-color: #fff; --footer-text-color: #fff; --quoteblock-color: #7a2518; --menu-burger-color: #fff; --various-border-color: #e7e7e9; } body.dark-theme { --admonition-background: #2a2929; --black-color: #fff; --white-color: #121212; --text-color: #aaa; --title-color: #fff; --header-color: rgba(255, 255, 255, 0.85); --footer-color: #121212; --footer-other-text-color: #ddd; --code-color: #1f1f1f; --code-text-color: rgba(255, 255, 255, 0.9); --code-link-color: #1fafcc; --num-color: #fff; --nav-color: #121212; --table-color: #121212; --box-shadow-color: rgba(255, 255, 255, .15); --top-header-color: #242526; --footer-white-color: #242526; --footer-text-color: #aaa; --footer-form-color: #1BA8CB; --quoteblock-color: #1DA2BD; --menu-burger-color: #242526; --various-border-color: #242526; } @media (prefers-color-scheme: dark) { /* defaults to dark theme */ body { --admonition-background: #2a2929; --black-color: #fff; --white-color: #121212; --text-color: #aaa; --title-color: #fff; --header-color: rgba(255, 255, 255, 0.85); --footer-color: #121212; --footer-other-text-color: #ddd; --code-color: #1f1f1f; --code-text-color: rgba(255, 255, 255, 0.9); --code-link-color: #1fafcc; --num-color: #fff; --nav-color: #121212; --table-color: #121212; --box-shadow-color: rgba(255, 255, 255, .15); --top-header-color: #242526; --footer-white-color: #242526; --footer-text-color: #aaa; --footer-form-color: #1BA8CB; --quoteblock-color: #1DA2BD; --menu-burger-color: #242526; --various-border-color: #242526; } body.light-theme { --gradle-blue: #209BC4; --gradle-bg-dark: #010002; --gradle-bg-gray: #F8F8F8; --gradle-bg-white: #FFFFFF; --gradle-blue: #209BC4; --gradle-blue-lite: #4DC9C0; --gradle-blue-dark: #1b3262; --gradle-blue-darker: #19274f; --button-gradient-angle: 160deg; --caution-color: #e40046; --caution-on-color: #fff; --important-color: #802392; --important-on-color: #fff; --note-color: #2d7dd2; --note-on-color: #fff; --tip-color: #43b929; --tip-on-color: #fff; --warning-color: #f70; --warning-on-color: #fff; --admonition-background: #fafafa; --doc-icon-filter: invert(14.5%); --rem-base: 18; --black-color: #000; --white-color: #fff; --text-color: #02303A; --title-color: #02303A; --header-color: rgba(0, 0, 0, 0.85); --footer-color: #fff; --footer-other-text-color: #02303; --code-color: #f7f7f8; --code-text-color: rgba(0, 0, 0, 0.9); --code-link-color: #021274; --num-color: rgba(0, 0, 0, 0.8); --nav-color: #f8f8f7; --table-color: #f7f8f7; --box-shadow-color: rgba(0, 0, 0, .15); --top-header-color: #fff; --footer-white-color: #fff; --footer-text-color: #fff; --footer-form-color: #1BA8CB; --quoteblock-color: #7a2518; --menu-burger-color: #fff; --various-border-color: #e7e7e9; } } .cls-1 { fill: #02303a; } body.dark-theme { .cls-1 { fill: #fff; } } @media (prefers-color-scheme: dark) { .cls-1 { fill: #fff; } body.light-theme { .cls-1 { fill: #02303a; } } } /* Lato (normal, regular) */ @font-face { font-family: Lato; font-weight: 400; font-style: normal; src: url("https://assets.gradle.com/lato/fonts/lato-normal/lato-normal.woff2") format("woff2"), url("https://assets.gradle.com/lato/fonts/lato-normal/lato-normal.woff") format("woff"); } /* Lato (normal, italic) */ @font-face { font-display: swap; font-family: Lato; font-weight: 400; font-style: italic; src: url("https://assets.gradle.com/lato/fonts/lato-normal-italic/lato-normal-italic.woff2") format("woff2"), url("https://assets.gradle.com/lato/fonts/lato-normal-italic/lato-normal-italic.woff") format("woff"); } /* Lato (bold, regular) */ @font-face { font-display: swap; font-family: Lato; font-weight: 500; font-style: normal; src: url("https://assets.gradle.com/lato/fonts/lato-semibold/lato-semibold.woff2") format("woff2"), url("https://assets.gradle.com/lato/fonts/lato-semibold/lato-semibold.woff") format("woff"); } /* Lato (bold, regular) */ @font-face { font-display: swap; font-family: Lato; font-weight: 800; font-style: normal; src: url("https://assets.gradle.com/lato/fonts/lato-heavy/lato-heavy.woff2") format("woff2"), url("https://assets.gradle.com/lato/fonts/lato-heavy/lato-heavy.woff") format("woff"); } /* BEGIN asciidoc.css */ /*! normalize.css v2.1.2 | MIT License | git.io/normalize */ /* ========================================================================== HTML5 display definitions ========================================================================== */ /** Correct `block` display not defined in IE 8/9. */ article, aside, details, figcaption, figure, footer, header, hgroup, main, nav, section, summary { display: block; } /** Correct `inline-block` display not defined in IE 8/9. */ audio, canvas, video { display: inline-block; } /** Prevent modern browsers from displaying `audio` without controls. Remove excess height in iOS 5 devices. */ audio:not([controls]) { display: none; height: 0; } /** Address `[hidden]` styling not present in IE 8/9. Hide the `template` element in IE, Safari, and Firefox < 22. */ [hidden], template { display: none; } script { display: none !important; } /* ========================================================================== Base ========================================================================== */ /** 1. Set default font family to sans-serif. 2. Prevent iOS text size adjust after orientation change, without disabling user zoom. */ html { font-family: sans-serif; /* 1 */ -ms-text-size-adjust: 100%; /* 2 */ -webkit-text-size-adjust: 100%; /* 2 */ } /** Remove default margin. */ body { margin: 0; } /* ========================================================================== Links ========================================================================== */ /** Remove the gray background color from active links in IE 10. */ a { background: transparent; } /** Address `outline` inconsistency between Chrome and other browsers. */ a:focus { outline: thin dotted; } /** Improve readability when focused and also mouse hovered in all browsers. */ a:active, a:hover { outline: 0; } /* ========================================================================== Typography ========================================================================== */ /** Address variable `h1` font-size and margin within `section` and `article` contexts in Firefox 4+, Safari 5, and Chrome. */ h1 { font-size: 2em; margin: 0.67em 0; } /** Address styling not present in IE 8/9, Safari 5, and Chrome. */ abbr[title] { border-bottom: 1px dotted; } /** Address style set to `bolder` in Firefox 4+, Safari 5, and Chrome. */ b, strong { font-weight: bold; } /** Address styling not present in Safari 5 and Chrome. */ dfn { font-style: italic; } /** Address differences between Firefox and other browsers. */ hr { -moz-box-sizing: content-box; box-sizing: content-box; height: 0; } /** Address styling not present in IE 8/9. */ mark { background: #ff0; color: var(--black-color); } /** Correct font family set oddly in Safari 5 and Chrome. */ code, kbd, pre, samp { font-family: monospace, serif; font-size: 1em; } /** Improve readability of pre-formatted text in all browsers. */ pre { white-space: pre-wrap; } /** Set consistent quote types. */ q { quotes: "\201C""\201D""\2018""\2019"; } /** Address inconsistent and variable font size in all browsers. */ small { font-size: 80%; } /** Prevent `sub` and `sup` affecting `line-height` in all browsers. */ sub, sup { font-size: 75%; line-height: 0; position: relative; vertical-align: baseline; } sup { top: -0.5em; } sub { bottom: -0.25em; } /* ========================================================================== Embedded content ========================================================================== */ /** Remove border when inside `a` element in IE 8/9. */ img { border: 0; } /** Correct overflow displayed oddly in IE 9. */ svg:not(:root) { overflow: hidden; } /* ========================================================================== Figures ========================================================================== */ /** Address margin not present in IE 8/9 and Safari 5. */ figure { margin: 0; } /* ========================================================================== Forms ========================================================================== */ /** Define consistent border, margin, and padding. */ fieldset { border: 1px solid #c0c0c0; margin: 0 2px; padding: 0.35em 0.625em 0.75em; } /** 1. Correct `color` not being inherited in IE 8/9. 2. Remove padding so people aren't caught out if they zero out fieldsets. */ legend { border: 0; /* 1 */ padding: 0; /* 2 */ } /** 1. Correct font family not being inherited in all browsers. 2. Correct font size not being inherited in all browsers. 3. Address margins set differently in Firefox 4+, Safari 5, and Chrome. */ button, input, select, textarea { font-family: inherit; /* 1 */ font-size: 100%; /* 2 */ margin: 0; /* 3 */ } /** Address Firefox 4+ setting `line-height` on `input` using `!important` in the UA stylesheet. */ button, input { line-height: normal; } /** Address inconsistent `text-transform` inheritance for `button` and `select`. All other form control elements do not inherit `text-transform` values. Correct `button` style inheritance in Chrome, Safari 5+, and IE 8+. Correct `select` style inheritance in Firefox 4+ and Opera. */ button, select { text-transform: none; } /** 1. Avoid the WebKit bug in Android 4.0.* where (2) destroys native `audio` and `video` controls. 2. Correct inability to style clickable `input` types in iOS. 3. Improve usability and consistency of cursor style between image-type `input` and others. */ button, html input[type="button"], input[type="reset"], input[type="submit"] { -webkit-appearance: button; /* 2 */ cursor: pointer; /* 3 */ } /** Re-set default cursor for disabled elements. */ button[disabled], html input[disabled] { cursor: default; } /** 1. Address box sizing set to `content-box` in IE 8/9. 2. Remove excess padding in IE 8/9. */ input[type="checkbox"], input[type="radio"] { box-sizing: border-box; /* 1 */ padding: 0; /* 2 */ } /** 1. Address `appearance` set to `searchfield` in Safari 5 and Chrome. 2. Address `box-sizing` set to `border-box` in Safari 5 and Chrome (include `-moz` to future-proof). */ input[type="search"] { -webkit-appearance: textfield; /* 1 */ -moz-box-sizing: content-box; -webkit-box-sizing: content-box; /* 2 */ box-sizing: content-box; } /** Remove inner padding and search cancel button in Safari 5 and Chrome on OS X. */ input[type="search"]::-webkit-search-cancel-button, input[type="search"]::-webkit-search-decoration { -webkit-appearance: none; } /** Remove inner padding and border in Firefox 4+. */ button::-moz-focus-inner, input::-moz-focus-inner { border: 0; padding: 0; } /** 1. Remove default vertical scrollbar in IE 8/9. 2. Improve readability and alignment in all browsers. */ textarea { overflow: auto; /* 1 */ vertical-align: top; /* 2 */ } /* ========================================================================== Tables ========================================================================== */ /** Remove most spacing between table cells. */ table { border-collapse: collapse; border-spacing: 0; } meta.foundation-mq-small { font-family: "only screen and (min-width: 768px)"; width: 768px; } meta.foundation-mq-medium { font-family: "only screen and (min-width:1280px)"; width: 1280px; } meta.foundation-mq-large { font-family: "only screen and (min-width:1440px)"; width: 1440px; } *, *:before, *:after { -moz-box-sizing: border-box; -webkit-box-sizing: border-box; box-sizing: border-box; } html, body { font-size: 100%; } body { background: var(--white-color); color: var(--num-color); padding: 0; margin: 0; font-family: "Noto Serif", "DejaVu Serif", serif; font-weight: normal; font-style: normal; line-height: 1; position: relative; cursor: auto; } a:hover { cursor: pointer; } img, object, embed { max-width: 100%; height: auto; } object, embed { height: 100%; } img { -ms-interpolation-mode: bicubic; } #map_canvas img, #map_canvas embed, #map_canvas object, .map_canvas img, .map_canvas embed, .map_canvas object { max-width: none !important; } .left { float: left !important; } .right { float: right !important; } .text-left { text-align: left !important; } .text-right { text-align: right !important; } .text-center { text-align: center !important; } .text-justify { text-align: justify !important; } .hide { display: none; } .antialiased { -webkit-font-smoothing: antialiased; } img { display: inline-block; vertical-align: middle; } textarea { height: auto; min-height: 50px; } select { width: 100%; } object, svg { display: inline-block; vertical-align: middle; } .center { margin-left: auto; margin-right: auto; } .spread { width: 100%; } p.lead, .paragraph.lead>p, #preamble>.sectionbody>.paragraph:first-of-type p { font-size: 1.21875em; line-height: 1.6; } .subheader, .admonitionblock td.content>.title, .audioblock>.title, .exampleblock>.title, .imageblock>.title, .listingblock>.title, .literalblock>.title, .stemblock>.title, .openblock>.title, .paragraph>.title, .quoteblock>.title, table.tableblock>.title, .verseblock>.title, .videoblock>.title, .dlist>.title, .olist>.title, .ulist>.title, .qlist>.title, .hdlist>.title { line-height: 1.45; color: #7a2518; font-weight: normal; margin-top: 0; margin-bottom: 0.25em; } /* Typography resets */ div, dl, dt, dd, ul, ol, li, h1, h2, h3, #toctitle, .sidebarblock>.content>.title, h4, h5, h6, pre, form, p, blockquote, th, td { margin: 0; padding: 0; direction: ltr; } /* Default Link Styles */ a { color: #2156a5; text-decoration: underline; line-height: inherit; } a:hover, a:focus { color: #1d4b8f; } a img { border: none; } /* Default paragraph styles */ p { font-family: inherit; font-weight: normal; font-size: 1em; line-height: 1.6; margin-bottom: 1.25em; text-rendering: optimizeLegibility; } p aside { font-size: 0.875em; line-height: 1.35; font-style: italic; } /* Default header styles */ h1, h2, h3, #toctitle, .sidebarblock>.content>.title, h4, h5, h6 { font-family: "Open Sans", "DejaVu Sans", sans-serif; font-weight: 300; font-style: normal; color: #ba3925; text-rendering: optimizeLegibility; margin-top: 1em; margin-bottom: 0.5em; line-height: 1.0125em; } h1 small, h2 small, h3 small, #toctitle small, .sidebarblock>.content>.title small, h4 small, h5 small, h6 small { font-size: 60%; color: #e99b8f; line-height: 0; } h1 { font-size: 2.125em; } h2 { font-size: 1.6875em; } h3, #toctitle, .sidebarblock>.content>.title { font-size: 1.375em; } h4 { font-size: 1.125em; } h5 { font-size: 1.125em; } h6 { font-size: 1em; } hr { border: solid #ddddd8; border-width: 1px 0 0; clear: both; margin: 1.25em 0 1.1875em; height: 0; } /* Helpful Typography Defaults */ em, i { font-style: italic; line-height: inherit; } strong, b { font-weight: bold; line-height: inherit; } small { font-size: 60%; line-height: inherit; } code { font-family: "Droid Sans Mono", "DejaVu Sans Mono", monospace; font-weight: normal; color: var(--code-text-color); } a code { color: var(--code-link-color); } /* Lists */ ul, ol, dl { font-size: 1em; line-height: 1.6; margin-bottom: 1.25em; list-style-position: outside; font-family: inherit; } ul, ol { margin-left: 1.5em; } ul.no-bullet, ol.no-bullet { margin-left: 1.5em; } /* Unordered Lists */ ul li ul, ul li ol { margin-left: 1.25em; margin-bottom: 0; font-size: 1em; /* Override nested font-size change */ } ul.square li ul, ul.circle li ul, ul.disc li ul { list-style: inherit; } ul.square { list-style-type: square; } ul.circle { list-style-type: circle; } ul.disc { list-style-type: disc; } ul.no-bullet { list-style: none; } /* Ordered Lists */ ol li ul, ol li ol { margin-left: 1.25em; margin-bottom: 0; } /* Definition Lists */ dl dt { margin-bottom: 0.3125em; font-weight: bold; } dl dd { margin-bottom: 1.25em; } /* Abbreviations */ abbr, acronym { text-transform: uppercase; font-size: 90%; color: var(--num-color); border-bottom: 1px dotted #dddddd; cursor: help; } abbr { text-transform: none; } /* Blockquotes */ blockquote { margin: 0 0 1.25em; padding: 0.5625em 1.25em 0 1.1875em; border-left: 1px solid #dddddd; } blockquote cite { display: block; font-size: 0.9375em; color: rgba(0, 0, 0, 0.6); } blockquote cite:before { content: "\2014 \0020"; } blockquote cite a, blockquote cite a:visited { color: rgba(0, 0, 0, 0.6); } blockquote, blockquote p { line-height: 1.6; color: var(--header-color); } /* Microformats */ .vcard { display: inline-block; margin: 0 0 1.25em 0; border: 1px solid #dddddd; padding: 0.625em 0.75em; } .vcard li { margin: 0; display: block; } .vcard .fn { font-weight: bold; font-size: 0.9375em; } .vevent .summary { font-weight: bold; } .vevent abbr { cursor: auto; text-decoration: none; font-weight: bold; border: none; padding: 0 0.0625em; } @media only screen and (min-width: 768px) { h1, h2, h3, #toctitle, .sidebarblock>.content>.title, h4, h5, h6 { line-height: 1.2; } h1 { font-size: 2.75em; } h2 { font-size: 2.3125em; } h3, #toctitle, .sidebarblock>.content>.title { font-size: 1.6875em; } h4 { font-size: 1.4375em; } } /* Tables */ table { background: var(--white-color); margin-bottom: 1.25em; border: solid 1px #dedede; } table thead, table tfoot { background: var(--table-color); font-weight: bold; } table thead tr th, table thead tr td, table tfoot tr th, table tfoot tr td { padding: 0.5em 0.625em 0.625em; font-size: inherit; color: var(--num-color); text-align: left; } table tr th, table tr td { padding: 0.5625em 0.625em; font-size: inherit; color: var(--num-color); } table tr.even, table tr.alt, table tr:nth-of-type(even) { background: var(--nav-color); } table thead tr th, table tfoot tr th, table tbody tr td, table tr td, table tfoot tr td { display: table-cell; line-height: 1.6; } body { tab-size: 4; } h1, h2, h3, #toctitle, .sidebarblock>.content>.title, h4, h5, h6 { line-height: 1.2; word-spacing: -0.05em; } h1 strong, h2 strong, h3 strong, #toctitle strong, .sidebarblock>.content>.title strong, h4 strong, h5 strong, h6 strong { font-weight: 400; } .clearfix:before, .clearfix:after, .float-group:before, .float-group:after { content: " "; display: table; } .clearfix:after, .float-group:after { clear: both; } *:not(pre)>code { font-size: 0.9375em; font-style: normal !important; letter-spacing: 0; padding: 0.1em 0.5ex; word-spacing: -0.15em; background-color: var(--code-color); -webkit-border-radius: 4px; border-radius: 4px; line-height: 1.45; text-rendering: optimizeSpeed; word-wrap: break-word; } *:not(pre)>code.nobreak { word-wrap: normal; } *:not(pre)>code.nowrap { white-space: nowrap; } pre, pre>code { line-height: 1.45; color: var(--code-text-color); font-family: "Droid Sans Mono", "DejaVu Sans Mono", "Monospace", monospace; font-weight: normal; text-rendering: optimizeSpeed; } em em { font-style: normal; } strong strong { font-weight: normal; } .keyseq { color: rgba(51, 51, 51, 0.8); } kbd { font-family: "Droid Sans Mono", "DejaVu Sans Mono", monospace; display: inline-block; color: var(--num-color); font-size: 0.65em; line-height: 1.45; background-color: #f7f7f7; border: 1px solid #ccc; -webkit-border-radius: 3px; border-radius: 3px; -webkit-box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 0.1em white inset; box-shadow: 0 1px 0 rgba(0, 0, 0, 0.2), 0 0 0 0.1em white inset; margin: 0 0.15em; padding: 0.2em 0.5em; vertical-align: middle; position: relative; top: -0.1em; white-space: nowrap; } .keyseq kbd:first-child { margin-left: 0; } .keyseq kbd:last-child { margin-right: 0; } .menuseq, .menu { color: var(--num-color); } b.button:before, b.button:after { position: relative; top: -1px; font-weight: normal; } b.button:before { content: "["; padding: 0 3px 0 2px; } b.button:after { content: "]"; padding: 0 2px 0 3px; } p a>code:hover { color: var(--code-text-color); } #header, #content, #footnotes, #footer { width: 100%; margin-left: auto; margin-right: auto; margin-top: 0; margin-bottom: 0; max-width: 62.5em; *zoom: 1; position: relative; padding-left: 0.9375em; padding-right: 0.9375em; } #header:before, #header:after, #content:before, #content:after, #footnotes:before, #footnotes:after, #footer:before, #footer:after { content: " "; display: table; } #header:after, #content:after, #footnotes:after, #footer:after { clear: both; } #content { margin-top: 1.25em; } #content:before { content: none; } #header>h1:first-child { color: var(--header-color); margin-top: 2.25rem; margin-bottom: 0; } #header>h1:first-child+#toc { margin-top: 8px; border-top: 1px solid #ddddd8; } #header>h1:only-child, body.toc2 #header>h1:nth-last-child(2) { border-bottom: 1px solid #ddddd8; padding-bottom: 8px; } #header .details { border-bottom: 1px solid #ddddd8; line-height: 1.45; padding-top: 0.25em; padding-bottom: 0.25em; padding-left: 0.25em; color: rgba(0, 0, 0, 0.6); display: -ms-flexbox; display: -webkit-flex; display: flex; -ms-flex-flow: row wrap; -webkit-flex-flow: row wrap; flex-flow: row wrap; } #header .details span:first-child { margin-left: -0.125em; } #header .details span.email a { color: var(--header-color); } #header .details br { display: none; } #header .details br+span:before { content: "\00a0\2013\00a0"; } #header .details br+span.author:before { content: "\00a0\22c5\00a0"; color: var(--header-color); } #header .details br+span#revremark:before { content: "\00a0|\00a0"; } #header #revnumber { text-transform: capitalize; } #header #revnumber:after { content: "\00a0"; } #content>h1:first-child:not([class]) { color: var(--header-color); border-bottom: 1px solid #ddddd8; padding-bottom: 8px; margin-top: 0; padding-top: 1rem; margin-bottom: 1.25rem; } #toc { border-bottom: 1px solid #efefed; padding-bottom: 0.5em; } #toc>ul { margin-left: 0.125em; } #toc ul.sectlevel0>li>a { font-style: italic; } #toc ul.sectlevel0 ul.sectlevel1 { margin: 0.5em 0; } #toc ul { font-family: "Open Sans", "DejaVu Sans", sans-serif; list-style-type: none; } #toc li { line-height: 1.3334; margin-top: 0.3334em; } #toc a { text-decoration: none; } #toc a:active { text-decoration: underline; } #toctitle { color: #7a2518; font-size: 1.2em; } @media only screen and (min-width: 768px) { #toctitle { font-size: 1.375em; } body.toc2 { padding-left: 15em; padding-right: 0; } #toc.toc2 { margin-top: 0 !important; background-color: var(--nav-color); position: fixed; width: 15em; left: 0; top: 0; border-right: 1px solid #efefed; border-top-width: 0 !important; border-bottom-width: 0 !important; z-index: 1000; padding: 1.25em 1em; height: 100%; overflow: auto; } #toc.toc2 #toctitle { margin-top: 0; margin-bottom: 0.8rem; font-size: 1.2em; } #toc.toc2>ul { font-size: 0.9em; margin-bottom: 0; } #toc.toc2 ul ul { margin-left: 0; padding-left: 1em; } #toc.toc2 ul.sectlevel0 ul.sectlevel1 { padding-left: 0; margin-top: 0.5em; margin-bottom: 0.5em; } body.toc2.toc-right { padding-left: 0; padding-right: 15em; } body.toc2.toc-right #toc.toc2 { border-right-width: 0; border-left: 1px solid #efefed; left: auto; right: 0; } } @media only screen and (min-width: 1280px) { body.toc2 { padding-left: 20em; padding-right: 0; } #toc.toc2 { width: 20em; } #toc.toc2 #toctitle { font-size: 1.375em; } #toc.toc2>ul { font-size: 0.95em; } #toc.toc2 ul ul { padding-left: 1.25em; } body.toc2.toc-right { padding-left: 0; padding-right: 20em; } } #content #toc { border-style: solid; border-width: 1px; border-color: #e0e0dc; margin-bottom: 1.25em; padding: 1.25em; background: var(--nav-color); -webkit-border-radius: 4px; border-radius: 4px; } #content #toc> :first-child { margin-top: 0; } #content #toc> :last-child { margin-bottom: 0; } #footer { max-width: 100%; background-color: var(--num-color); padding: 1.25em; } #footer-text { color: rgba(255, 255, 255, 0.8); line-height: 1.44; } .sect1 { padding-bottom: 0.625em; } @media only screen and (min-width: 768px) { .sect1 { padding-bottom: 1.25em; } } .sect1+.sect1 { border-top: 1px solid #efefed; } #content h1>a.anchor, h2>a.anchor, h3>a.anchor, #toctitle>a.anchor, .sidebarblock>.content>.title>a.anchor, h4>a.anchor, h5>a.anchor, h6>a.anchor { position: absolute; z-index: 1001; width: 1.5ex; margin-left: -1.5ex; display: block; text-decoration: none !important; visibility: hidden; text-align: center; font-weight: normal; } #content h1>a.anchor:before, h2>a.anchor:before, h3>a.anchor:before, #toctitle>a.anchor:before, .sidebarblock>.content>.title>a.anchor:before, h4>a.anchor:before, h5>a.anchor:before, h6>a.anchor:before { content: "\00A7"; font-size: 0.85em; display: block; padding-top: 0.1em; } #content h1:hover>a.anchor, #content h1>a.anchor:hover, h2:hover>a.anchor, h2>a.anchor:hover, h3:hover>a.anchor, #toctitle:hover>a.anchor, .sidebarblock>.content>.title:hover>a.anchor, h3>a.anchor:hover, #toctitle>a.anchor:hover, .sidebarblock>.content>.title>a.anchor:hover, h4:hover>a.anchor, h4>a.anchor:hover, h5:hover>a.anchor, h5>a.anchor:hover, h6:hover>a.anchor, h6>a.anchor:hover { visibility: visible; } #content h1>a.link, h2>a.link, h3>a.link, #toctitle>a.link, .sidebarblock>.content>.title>a.link, h4>a.link, h5>a.link, h6>a.link { color: #ba3925; text-decoration: none; } #content h1>a.link:hover, h2>a.link:hover, h3>a.link:hover, #toctitle>a.link:hover, .sidebarblock>.content>.title>a.link:hover, h4>a.link:hover, h5>a.link:hover, h6>a.link:hover { color: #a53221; } .audioblock, .imageblock, .literalblock, .listingblock, .stemblock, .videoblock { margin-bottom: 1.25em; } .admonitionblock td.content>.title, .audioblock>.title, .exampleblock>.title, .imageblock>.title, .listingblock>.title, .literalblock>.title, .stemblock>.title, .openblock>.title, .paragraph>.title, .quoteblock>.title, table.tableblock>.title, .verseblock>.title, .videoblock>.title, .dlist>.title, .olist>.title, .ulist>.title, .qlist>.title, .hdlist>.title { text-rendering: optimizeLegibility; text-align: left; font-family: "Noto Serif", "DejaVu Serif", serif; font-size: 1rem; font-style: italic; } table.tableblock>caption.title { white-space: nowrap; overflow: visible; max-width: 0; } .paragraph.lead>p, #preamble>.sectionbody>.paragraph:first-of-type p { color: var(--header-color); } table.tableblock #preamble>.sectionbody>.paragraph:first-of-type p { font-size: inherit; } /* Custom SVG logos coloring */ path { fill: #02303A; } body.dark-theme { path { fill: white; } } @media (prefers-color-scheme: dark) { path { fill: white; } body.light-theme { path { fill: #02303A; } } } /* Custom scroll bar */ /* Works on Firefox */ .docs-navigation { scrollbar-width: auto; scrollbar-color: #686868 #e7e7e9; } /* Works on Chrome, Edge, and Safari */ .docs-navigation::-webkit-scrollbar { width: 12px; } .docs-navigation::-webkit-scrollbar-track { background: #e7e7e9; } .docs-navigation::-webkit-scrollbar-thumb { background-color: #686868; border-radius: 20px; border: 3px #686868; } body.dark-theme { /* Works on Firefox */ * { scrollbar-width: auto; scrollbar-color: #686868 #242526; } /* Works on Chrome, Edge, and Safari */ *::-webkit-scrollbar { width: auto; } *::-webkit-scrollbar-track { background: #242526; } *::-webkit-scrollbar-thumb { background-color: #686868; border-radius: 20px; border: 3px #686868; } } @media (prefers-color-scheme: dark) { /* Works on Firefox */ * { scrollbar-width: auto; scrollbar-color: #686868 #242526; } /* Works on Chrome, Edge, and Safari */ *::-webkit-scrollbar { width: auto; } *::-webkit-scrollbar-track { background: #242526; } *::-webkit-scrollbar-thumb { background-color: #686868; border-radius: 20px; border: 3px #686868; } body.light-theme { .docs-navigation { scrollbar-width: auto; scrollbar-color: #686868 #e7e7e9; } /* Works on Chrome, Edge, and Safari */ .docs-navigation::-webkit-scrollbar { width: 12px; } .docs-navigation::-webkit-scrollbar-track { background: #e7e7e9; } .docs-navigation::-webkit-scrollbar-thumb { background-color: #686868; border-radius: 20px; border: 3px #686868; } } } /* Custom Admonition Blocks - Icons from https://github.com/primer/octicons */ .admonitionblock td div:last-of-type p { margin-bottom: 0em !important; } .admonitionblock { margin: 1.4rem 0 0 } .admonitionblock i { font-family: inherit; } .admonitionblock i.fa { background: no-repeat 50%/1em 1em; display: inline-block; filter: var(--doc-icon-filter); font-style: normal; height: 1em; -webkit-hyphens: none; hyphens: none; vertical-align: -.125em; width: 1em } .admonitionblock p, .admonitionblock td.content { font-size: 1rem; } .admonitionblock td.content>.title+*, .admonitionblock td.content>:not(.title):first-child { margin-top: 0 } .admonitionblock pre { font-size: calc(15/var(--rem-base)*1rem) } .admonitionblock>table { position: relative; table-layout: fixed; border: none; width: 100% } .admonitionblock td.content { word-wrap: anywhere; background: var(--admonition-background); padding: 1rem 1rem 1rem 1rem; width: 100%; border-radius: 4px; } .admonitionblock td.icon { background: linear-gradient(90deg, rgba(0, 0, 0, .2) 0, rgba(0, 0, 0, .2)) no-repeat 0 /2.075em 100%; border-radius: .5em; font-size: calc(15/var(--rem-base)*1rem); left: 0; line-height: 1; padding: .25em .075em; position: absolute; top: 0; transform: translate(-.5rem, -50%) } .admonitionblock td.icon i { align-items: center; background-position-x: .5em; display: inline-flex; filter: invert(100%); padding-left: 2em; vertical-align: initial; width: auto } .admonitionblock td.icon i::after { content: attr(title); filter: invert(100%); font-style: normal; font-weight: bold; margin: -.05em; padding: 0 .5em; text-transform: uppercase } .admonitionblock.caution td.icon { background-color: var(--caution-color); color: var(--caution-on-color) } .admonitionblock.caution td.icon i { background-image: url(./img/octicons-16.svg#view-flame) } .admonitionblock.important td.icon { background-color: var(--important-color); color: var(--important-on-color) } .admonitionblock.important td.icon i { background-image: url(./img/octicons-16.svg#view-stop) } .admonitionblock.note td.icon { background-color: var(--note-color); color: var(--note-on-color) } .admonitionblock.note td.icon i { background-image: url(./img/octicons-16.svg#view-info) } .admonitionblock.tip td.icon { background-color: var(--tip-color); color: var(--tip-on-color) } .admonitionblock.tip td.icon i { background-image: url(./img/octicons-16.svg#view-light-bulb) } .admonitionblock.warning td.icon { background-color: var(--warning-color); color: var(--warning-on-color) } .admonitionblock.warning td.icon i { background-image: url(./img/octicons-16.svg#view-alert) } /* Custom collapsible block */ details summary { width: 100%; padding: 1rem 0; border-top: 1px solid gray; position: relative; cursor: pointer; list-style: none; } details summary:after { content: "+"; color: var(--black-color); position: absolute; font-size: 1.75rem; line-height: 0; margin-top: 0.3rem; right: 0; font-weight: 400; transform-origin: center; transition: 200ms linear; } details[open] summary:after { transform: rotate(45deg); font-size: 2rem; } details summary { outline: 0; } details p { font-size: 0.95rem; margin: 0 0 1rem; padding-top: 1rem; } .exampleblock>.content { border-style: solid; border-width: 1px; border-color: #e6e6e6; margin-bottom: 1.25em; padding: 1.25em; background: var(--white-color); -webkit-border-radius: 4px; border-radius: 4px; } .exampleblock>.content> :first-child { margin-top: 0; } .exampleblock>.content> :last-child { margin-bottom: 0; } .sidebarblock { border-style: solid; border-width: 1px; border-color: #e0e0dc; margin-bottom: 1.25em; padding: 1.25em; background: var(--nav-color); -webkit-border-radius: 4px; border-radius: 4px; } .sidebarblock> :first-child { margin-top: 0; } .sidebarblock> :last-child { margin-bottom: 0; } .sidebarblock>.content>.title { color: #7a2518; margin-top: 0; text-align: center; } .exampleblock>.content> :last-child> :last-child, .exampleblock>.content .olist>ol>li:last-child> :last-child, .exampleblock>.content .ulist>ul>li:last-child> :last-child, .exampleblock>.content .qlist>ol>li:last-child> :last-child, .sidebarblock>.content> :last-child> :last-child, .sidebarblock>.content .olist>ol>li:last-child> :last-child, .sidebarblock>.content .ulist>ul>li:last-child> :last-child, .sidebarblock>.content .qlist>ol>li:last-child> :last-child { margin-bottom: 0; } .literalblock pre, .listingblock pre:not(.highlight), .listingblock pre[class="highlight"], .listingblock pre[class^="highlight "], .listingblock pre.CodeRay, .listingblock pre.prettyprint { background: var(--code-color); } .sidebarblock .literalblock pre, .sidebarblock .listingblock pre:not(.highlight), .sidebarblock .listingblock pre[class="highlight"], .sidebarblock .listingblock pre[class^="highlight "], .sidebarblock .listingblock pre.CodeRay, .sidebarblock .listingblock pre.prettyprint { background: #f2f1f1; } .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { -webkit-border-radius: 4px; border-radius: 4px; word-wrap: break-word; padding: 1em; font-size: 0.8125em; } .literalblock pre.nowrap, .literalblock pre[class].nowrap, .listingblock pre.nowrap, .listingblock pre[class].nowrap { overflow-x: auto; white-space: pre; word-wrap: normal; } @media only screen and (min-width: 768px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 0.90625em; } } @media only screen and (min-width: 1280px) { .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { font-size: 1em; } } .literalblock.output pre { color: var(--code-color); background-color: var(--code-text-color); } .listingblock pre.highlightjs { padding: 0; } .listingblock pre.highlightjs>code { padding: 1em; -webkit-border-radius: 4px; border-radius: 4px; } .listingblock pre.prettyprint { border-width: 0; } .listingblock>.content { position: relative; } .listingblock code[data-lang]:before { display: none; content: attr(data-lang); position: absolute; font-size: 0.75em; top: 0.425rem; right: 0.5rem; line-height: 1; text-transform: uppercase; color: #999; } .listingblock:hover code[data-lang]:before { display: block; } .listingblock.terminal pre .command:before { content: attr(data-prompt); padding-right: 0.5em; color: #999; } .listingblock.terminal pre .command:not([data-prompt]):before { content: "$"; } table.pyhltable { border-collapse: separate; border: 0; margin-bottom: 0; background: none; } table.pyhltable td { vertical-align: top; padding-top: 0; padding-bottom: 0; line-height: 1.45; } table.pyhltable td.code { padding-left: .75em; padding-right: 0; } pre.pygments .lineno, table.pyhltable td:not(.code) { color: #999; padding-left: 0; padding-right: .5em; border-right: 1px solid #ddddd8; } pre.pygments .lineno { display: inline-block; margin-right: .25em; } table.pyhltable .linenodiv { background: none !important; padding-right: 0 !important; } .quoteblock { margin: 0 1em 1.25em 1.5em; display: table; } .quoteblock>.title { margin-left: -1.5em; margin-bottom: 0.75em; } .quoteblock blockquote, .quoteblock blockquote p { color: var(--header-color); font-size: 1.15rem; line-height: 1.75; word-spacing: 0.1em; letter-spacing: 0; font-style: italic; text-align: justify; } .quoteblock blockquote { margin: 0; padding: 0; border: 0; } .quoteblock blockquote:before { content: "\201c"; float: left; font-size: 2.75em; font-weight: bold; line-height: 0.6em; margin-left: -0.6em; color: var(--quoteblock-color); text-shadow: 0 1px 2px rgba(0, 0, 0, 0.1); } .quoteblock blockquote>.paragraph:last-child p { margin-bottom: 0; } .quoteblock .attribution { margin-top: 0.5em; margin-right: 0.5ex; text-align: right; } .quoteblock .quoteblock { margin-left: 0; margin-right: 0; padding: 0.5em 0; border-left: 3px solid rgba(0, 0, 0, 0.6); } .quoteblock .quoteblock blockquote { padding: 0 0 0 0.75em; } .quoteblock .quoteblock blockquote:before { display: none; } .verseblock { margin: 0 1em 1.25em 1em; } .verseblock pre { font-family: "Open Sans", "DejaVu Sans", sans; font-size: 1.15rem; color: var(--header-color); font-weight: 300; text-rendering: optimizeLegibility; } .verseblock pre strong { font-weight: 400; } .verseblock .attribution { margin-top: 1.25rem; margin-left: 0.5ex; } .quoteblock .attribution, .verseblock .attribution { font-size: 0.9375em; line-height: 1.45; font-style: italic; } .quoteblock .attribution br, .verseblock .attribution br { display: none; } .quoteblock .attribution cite, .verseblock .attribution cite { display: block; letter-spacing: -0.025em; color: rgba(0, 0, 0, 0.6); } .quoteblock.abstract { margin: 0 0 1.25em 0; display: block; } .quoteblock.abstract blockquote, .quoteblock.abstract blockquote p { text-align: left; word-spacing: 0; } .quoteblock.abstract blockquote:before, .quoteblock.abstract blockquote p:first-of-type:before { display: none; } table.tableblock { max-width: 100%; border-collapse: separate; } table.tableblock td>.paragraph:last-child p>p:last-child, table.tableblock th>p:last-child, table.tableblock td>p:last-child { margin-bottom: 0; } table.tableblock, th.tableblock, td.tableblock { border: 0 solid #dedede; } table.grid-all th.tableblock, table.grid-all td.tableblock { border-width: 0 1px 1px 0; } table.grid-all tfoot>tr>th.tableblock, table.grid-all tfoot>tr>td.tableblock { border-width: 1px 1px 0 0; } table.grid-cols th.tableblock, table.grid-cols td.tableblock { border-width: 0 1px 0 0; } table.grid-all *>tr>.tableblock:last-child, table.grid-cols *>tr>.tableblock:last-child { border-right-width: 0; } table.grid-rows th.tableblock, table.grid-rows td.tableblock { border-width: 0 0 1px 0; } table.grid-all tbody>tr:last-child>th.tableblock, table.grid-all tbody>tr:last-child>td.tableblock, table.grid-all thead:last-child>tr>th.tableblock, table.grid-rows tbody>tr:last-child>th.tableblock, table.grid-rows tbody>tr:last-child>td.tableblock, table.grid-rows thead:last-child>tr>th.tableblock { border-bottom-width: 0; } table.grid-rows tfoot>tr>th.tableblock, table.grid-rows tfoot>tr>td.tableblock { border-width: 1px 0 0 0; } table.frame-all { border-width: 1px; } table.frame-sides { border-width: 0 1px; } table.frame-topbot { border-width: 1px 0; } th.halign-left, td.halign-left { text-align: left; } th.halign-right, td.halign-right { text-align: right; } th.halign-center, td.halign-center { text-align: center; } th.valign-top, td.valign-top { vertical-align: top; } th.valign-bottom, td.valign-bottom { vertical-align: bottom; } th.valign-middle, td.valign-middle { vertical-align: middle; } table thead th, table tfoot th { font-weight: bold; } tbody tr th { display: table-cell; line-height: 1.6; background: var(--table-color); } tbody tr th, tbody tr th p, tfoot tr th, tfoot tr th p { color: var(--num-color); font-weight: bold; } p.tableblock>code:only-child { background: none; padding: 0; } p.tableblock { font-size: 1em; } td>div.verse { white-space: pre; } ol { margin-left: 1.75em; } ul li ol { margin-left: 1.5em; } dl dd { margin-left: 1.125em; } dl dd:last-child, dl dd:last-child> :last-child { margin-bottom: 0; } ol>li p, ul>li p, ul dd, ol dd, .olist .olist, .ulist .ulist, .ulist .olist, .olist .ulist { margin-bottom: 0.625em; } ul.unstyled, ol.unnumbered, ul.checklist, ul.none { list-style-type: none; } ul.unstyled, ol.unnumbered, ul.checklist { margin-left: 0.625em; } ul.checklist li>p:first-child>.fa-square-o:first-child, ul.checklist li>p:first-child>.fa-check-square-o:first-child { width: 1em; font-size: 0.85em; } ul.checklist li>p:first-child>input[type="checkbox"]:first-child { width: 1em; position: relative; top: 1px; } ul.inline { margin: 0 auto 0.625em auto; margin-left: -1.375em; margin-right: 0; padding: 0; list-style: none; overflow: hidden; } ul.inline>li { list-style: none; float: left; margin-left: 1.375em; display: block; } ul.inline>li>* { display: block; } .unstyled dl dt { font-weight: normal; font-style: normal; } ol.arabic { list-style-type: decimal; } ol.decimal { list-style-type: decimal-leading-zero; } ol.loweralpha { list-style-type: lower-alpha; } ol.upperalpha { list-style-type: upper-alpha; } ol.lowerroman { list-style-type: lower-roman; } ol.upperroman { list-style-type: upper-roman; } ol.lowergreek { list-style-type: lower-greek; } .hdlist>table, .colist>table { border: 0; background: none; } .hdlist>table>tbody>tr, .colist>table>tbody>tr { background: none; } td.hdlist1, td.hdlist2 { vertical-align: top; padding: 0 0.625em; } td.hdlist1 { font-weight: bold; padding-bottom: 1.25em; } .literalblock+.colist { margin-top: -0.5em; } .colist>table tr>td:first-of-type { padding: 0 0.75em; line-height: 1; } .colist>table tr>td:first-of-type img { max-width: initial; } .colist>table tr>td:last-of-type { padding: 0.25em 0; } .thumb, .th { line-height: 0; display: inline-block; border: solid 4px var(--white-color); -webkit-box-shadow: 0 0 0 1px #dddddd; box-shadow: 0 0 0 1px #dddddd; } .imageblock.left, .imageblock[style*="float: left"] { margin: 0.25em 0.625em 1.25em 0; } .imageblock.right, .imageblock[style*="float: right"] { margin: 0.25em 0 1.25em 0.625em; } .imageblock>.title { margin-bottom: 0; } .imageblock.thumb, .imageblock.th { border-width: 6px; } .imageblock.thumb>.title, .imageblock.th>.title { padding: 0 0.125em; } .image.left, .image.right { margin-top: 0.25em; margin-bottom: 0.25em; display: inline-block; line-height: 0; } .image.left { margin-right: 0.625em; } .image.right { margin-left: 0.625em; } a.image { text-decoration: none; display: inline-block; } a.image object { pointer-events: none; } sup.footnote, sup.footnoteref { font-size: 0.875em; position: static; vertical-align: super; } sup.footnote a, sup.footnoteref a { text-decoration: none; } sup.footnote a:active, sup.footnoteref a:active { text-decoration: underline; } #footnotes { padding-top: 0.75em; padding-bottom: 0.75em; margin-bottom: 0.625em; } #footnotes hr { width: 20%; min-width: 6.25em; margin: -0.25em 0 0.75em 0; border-width: 1px 0 0 0; } #footnotes .footnote { padding: 0 0.375em 0 0.225em; line-height: 1.3334; font-size: 0.875em; margin-left: 1.2em; text-indent: -1.05em; margin-bottom: 0.2em; } #footnotes .footnote a:first-of-type { font-weight: bold; text-decoration: none; } #footnotes .footnote:last-of-type { margin-bottom: 0; } #content #footnotes { margin-top: -0.625em; margin-bottom: 0; padding: 0.75em 0; } .gist .file-data>table { border: 0; background: var(--white-color); width: 100%; margin-bottom: 0; } .gist .file-data>table td.line-data { width: 99%; } div.unbreakable { page-break-inside: avoid; } .big { font-size: larger; } .small { font-size: smaller; } .underline { text-decoration: underline; } .overline { text-decoration: overline; } .line-through { text-decoration: line-through; } .green { color: #006000; } .red { color: #bf0000; } .yellow { color: #bfbf00; } span.icon>.fa { cursor: default; } .conum[data-value] { display: inline-block; color: var(--white-color) !important; background-color: var(--num-color); -webkit-border-radius: 100px; border-radius: 100px; text-align: center; font-size: 0.75em; width: 1.67em; height: 1.67em; line-height: 1.67em; font-family: "Open Sans", "DejaVu Sans", sans-serif; font-style: normal; font-weight: bold; } .conum[data-value] * { color: var(--white-color) !important; } .conum[data-value]+b { display: none; } .conum[data-value]:after { content: attr(data-value); } pre .conum[data-value] { position: relative; top: -0.125em; } b.conum * { color: inherit !important; } .conum:not([data-value]):empty { display: none; } dt, th.tableblock, td.content, div.footnote { text-rendering: optimizeLegibility; } h1, h2, p, td.content, span.alt { letter-spacing: -0.01em; } p strong, td.content strong, div.footnote strong { letter-spacing: -0.005em; } p, blockquote, dt, td.content, span.alt { font-size: 1.0625rem; } p { margin-bottom: 1.25rem; } .sidebarblock p, .sidebarblock dt, .sidebarblock td.content, p.tableblock { font-size: 1em; } .exampleblock>.content { background-color: #fffef7; border-color: #e0e0dc; -webkit-box-shadow: 0 1px 4px #e0e0dc; box-shadow: 0 1px 4px #e0e0dc; } .print-only { display: none !important; } @media print { @page { margin: 1.25cm 0.75cm; } * { -webkit-box-shadow: none !important; box-shadow: none !important; text-shadow: none !important; } a { color: inherit !important; text-decoration: underline !important; } a.bare, a[href^="#"], a[href^="mailto:"] { text-decoration: none !important; } a[href^="http:"]:not(.bare):after, a[href^="https:"]:not(.bare):after { content: "(" attr(href) ")"; display: inline-block; font-size: 0.875em; padding-left: 0.25em; } abbr[title]:after { content: " (" attr(title) ")"; } pre, blockquote, tr, img, object, svg { page-break-inside: avoid; } thead { display: table-header-group; } svg { max-width: 100%; } p, blockquote, dt, td.content { font-size: 1em; orphans: 3; widows: 3; } h2, h3, #toctitle, .sidebarblock>.content>.title, #toctitle, .sidebarblock>.content>.title { page-break-after: avoid; } #toc, .sidebarblock, .exampleblock>.content { background: none !important; } #toc { border-bottom: 1px solid #ddddd8 !important; padding-bottom: 0 !important; } .sect1 { padding-bottom: 0 !important; } .sect1+.sect1 { border: 0 !important; } #header>h1:first-child { margin-top: 1.25rem; } body.book #header { text-align: center; } body.book #header>h1:first-child { border: 0 !important; margin: 2.5em 0 1em 0; } body.book #header .details { border: 0 !important; display: block; padding: 0 !important; } body.book #header .details span:first-child { margin-left: 0 !important; } body.book #header .details br { display: block; } body.book #header .details br+span:before { content: none !important; } body.book #toc { border: 0 !important; text-align: left !important; padding: 0 !important; margin: 0 !important; } body.book #toc, body.book #preamble, body.book h1.sect0, body.book .sect1>h2 { page-break-before: always; } .listingblock code[data-lang]:before { display: block; } #footer { background: none !important; padding: 0 0.9375em; } #footer-text { color: rgba(0, 0, 0, 0.6) !important; font-size: 0.9em; } .hide-on-print { display: none !important; } .print-only { display: block !important; } .hide-for-print { display: none !important; } .show-for-print { display: inherit !important; } } /* END asciidoc.css */ html, body { margin: 0; padding: 0; } html { font-size: 16px; font-weight: 400; line-height: 1.5; } body { color: var(--text-color); background-color: var(--white-color); font-family: "Lato", "Helvetica Neue", Arial, sans-serif; line-height: 1.5; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%; } /* Links */ a { color: #1DA2BD; text-decoration: none; } a:hover, a:focus { text-decoration: underline; } #content a[href^='../dsl/'], #content a[href^='../kotlin-dsl/'], #content a[href^='../javadoc/'] { font-family: 'Inconsolata', monospace; font-style: normal; border-bottom: 1px dotted rgba(29, 162, 189, 0.5); padding: 0 1px; } #content a[href^='../dsl/']:hover, #content a[href^='../dsl/']:focus, #content a[href^='../kotlin-dsl/']:hover, #content a[href^='../kotlin-dsl/']:focus, #content a[href^='../javadoc/']:hover, #content a[href^='../javadoc/']:focus { text-decoration: none; } /* Copy */ p { font-size: 1rem; } pre, pre>code, code { font-family: 'Inconsolata', monospace; } h1, h2, h3, h4, h5, h6, #toctitle, .sidebarblock>.content>.title { font-family: inherit; font-weight: 500; color: inherit; } h1 { font-size: 2rem; } h2 { font-size: 1.5rem; } h3 { font-size: 1.125rem; } h4 { font-size: 1.0625rem; } h5, h6 { font-size: 1rem; } b, strong { font-weight: 500; } dl { margin: 0 0 1.25rem 1.5rem; } .dlist dt code { color: var(--text-color); font-size: 1em; font-weight: bold; } .dlist p { margin-bottom: 0.625rem; } .sr-only { border: 0; clip: rect(0, 0, 0, 0); height: 1px; margin: -1px; overflow: hidden; padding: 0; position: absolute; width: 1px; } /* Layout */ .main-content>.appendix, .main-content>.book, .main-content>.chapter, .main-content>.footer { background-color: var(--white-color); border-radius: 5px; max-width: 45rem; padding: 1.5rem; } @media screen and (max-width: 45em) { .footer { max-width: 100%; } .main-content>.appendix, .main-content>.book, .main-content>.chapter { margin-top: 0; margin-bottom: 0; } } /* Override asciidoc styles */ #header { position: static; } #header, #content { padding: 0; } #header .details { /* TODO: Pretty sure there's a way to avoid Asciidoc generating details */ display: none; } p { color: var(--text-color); } h1, h2, p, p strong, td.content, td.content strong, div.footnote strong, span.alt { letter-spacing: normal; } .subheader, .admonitionblock td.content>.title, .audioblock>.title, .exampleblock>.title, .imageblock>.title, .listingblock>.title, .literalblock>.title, .stemblock>.title, .openblock>.title, .paragraph>.title, .quoteblock>.title, table.tableblock>.title, .verseblock>.title, .videoblock>.title, .dlist>.title, .olist>.title, .ulist>.title, .qlist>.title, .hdlist>.title { color: inherit; font-family: inherit; } .listingblock .title, .listingblock .title code { font-style: normal; font-weight: bold; } .imageblock, .videoblock { padding: 0.25em; } p.lead, .paragraph.lead>p, #preamble>.sectionbody>.paragraph:first-of-type p { font-size: 1.0625rem; } .paragraph.lead>p, #preamble>.sectionbody>.paragraph:first-of-type p { color: inherit; } .sect1 { padding-bottom: 0; } .sect1+.sect1 { border: 0 none; } .verseblock pre { font-family: "Lato", Arial, sans-serif; } td.hdlist1 { padding-bottom: 0.625rem; } td.hdlist2 p { margin-bottom: 0.625rem; } body.book #header>h1 { border: 0; } #header>h1:first-child { margin-top: 0; } #content a.link { color: var(--title-color); } .highlight .com { color: #777; } .listingblock pre.highlightjs>code { overflow-x: auto; } .listingblock pre.highlight { overflow-x: auto; } .listingblock pre.highlight>code { white-space: pre; } .conum[data-value] { font-family: "Lato", Arial, sans-serif; } .colist>table tr>td:first-of-type { padding-top: 0.25em; padding-bottom: 0.25em; line-height: 1.4; vertical-align: baseline; } /* * Samples */ .exampleblock>.content { background-color: inherit; border: 0 none; box-shadow: none; padding: 0; padding-bottom: 0.7rem; margin-bottom: 0; } .exampleblock>.content .title { background-color: var(--code-color); border-top: 1px solid #ccc; font-family: 'Inconsolata', monospace; margin: 0; padding: 1em 1em 0; } .exampleblock>.title>a { text-decoration: none; color: var(--num-color); } .exampleblock .listingblock { margin: 0; } /* * Ensure that blocks of code do not wrap by applying the behavior of `[listing%nowrap]` by default. * * These styles are copied from a CSS ruleset in asciidoctor.css that has the same group of * selectors except that they end with `.nowrap`. */ .openblock .content { background: var(--admonition-background); margin-bottom: 1.25em; padding: 1em 1em 0em 1em; border-radius: 4px; overflow: auto !important; } .literalblock pre, .literalblock pre[class], .listingblock pre, .listingblock pre[class] { overflow-x: auto; white-space: pre; word-wrap: normal; } /* * This CSS ruleset solves: https://github.com/gradle/guides/issues/113#issuecomment-314826749. */ .literalblock pre::after, .literalblock pre[class]::after, .listingblock pre::after, .listingblock pre[class]::after { content: ""; } .quoteblock blockquote, .quoteblock blockquote p { text-align: left; text-align: start; } div.screenshot { box-shadow: 0 0 20px 1px rgba(0, 0, 0, 0.2); margin-left: auto; margin-right: auto; width: 90%; } .inset { box-shadow: 0 0 1px 1px rgba(0, 0, 0, 0.1); padding: 1em; } .image.inline-icon img { vertical-align: sub; } /* TOC */ #header>h1:first-child+#toc { background: none; border: 0 none; margin-top: 0; } #toc, #content #toc { border: 0 none; } #toc>ul { margin-left: 0; font-family: inherit; } #toc>ul>li { line-height: 1.25; margin-top: 0; padding-bottom: 0.5rem; } #toc>ul>li:last-of-type { padding-bottom: 0; } #toc a { font-style: normal; } #toc a:hover, #toc a:focus, #toc a:hover code, #toc a:focus code { color: #1DA2BD; } #toc a:active { text-decoration: none; } /* Site header specific styles */ .hamburger { background-color: transparent; background-image: none; border: none; border-radius: 4px; cursor: pointer; margin-left: auto; padding: 11px 10px; } .hamburger:focus { outline: 0; } .hamburger__bar { display: block; width: 22px; height: 2px; background-color: var(--black-color); border-radius: 1px; } .hamburger__bar+.hamburger__bar { margin-top: 4px; } .site-header { background-color: var(--top-header-color); } /* Override javadoc styles */ .site-header div { font-family: 'Lato', Arial, sans-serif; } .site-header__navigation-header a { align-self: center; border-bottom: 0 none; height: 36px; } .site-header .site-header-version { align-self: center; color: #1da2bd; font-size: 20px; padding-left: 1px; margin-top: 22px; } .site-header__navigation { z-index: 2; display: flex; flex-direction: column; } .site-header__navigation-header { display: flex; flex: 0 0 auto; margin-left: 12px; } .site-header__navigation-collapsible { flex: 1 1 auto; height: 210px; overflow: visible; transition: height 0.3s ease; } .site-header__navigation-items { display: flex; flex-direction: column; flex-wrap: wrap; align-items: flex-start; max-height: 210px; /* This matches the collapsible height above */ margin: 0 20px; padding-top: 12px; padding-left: 0; list-style-type: none; } .site-header__navigation-item { flex: 0 1 auto; font-size: 16px; width: 250px; } .site-header__navigation-item .site-header__navigation-link { position: relative; display: inline-block; cursor: pointer; width: 100%; padding: 5px; line-height: 20px; border: 0 none; color: var(--text-color); text-decoration: none; transition: none; -o-transition: none; -moz-transition: none; -webkit-transition: none; } .site-header__navigation-item .site-header__navigation-link:hover { color: #1DA2BD; } .site-header__navigation-item .site-header__navigation-link.active { font-weight: 500; } /* Navigation submenu styles */ .site-header__navigation-submenu-section { position: relative; } .site-header__navigation-submenu-section .site-header__down-arrow { width: 8px; height: 8px; margin-left: 2px; margin-top: 0; } .site-header__navigation-submenu-section .site-header__navigation-link:hover path { fill: none; } .site-header__navigation-submenu-section .site-header__navigation-submenu .site-header__navigation-submenu-item-link:hover { color: #1DA2BD; } .site-header__navigation-submenu-section .site-header__navigation-submenu { display: none; width: 170px; background-color: var(--menu-burger-color); top: 40px; left: 7px; /* NOTE: This must match the padding of .site-header__navigation-link */ padding: 3px 10px 6px 10px; z-index: 100; } .site-header__navigation-submenu-section .site-header__navigation-submenu .site-header__navigation-submenu-item-link { width: 100%; color: var(--text-color); white-space: nowrap; display: inline-block; padding-top: 3px; border: 0 none; transition: none; -o-transition: none; -moz-transition: none; -webkit-transition: none; } .site-header__navigation-submenu-section .site-header__navigation-submenu .site-header__navigation-submenu-item-link .site-header__navigation-submenu-item-link-text { display: inline-block; font-size: 16px; } .site-header__navigation-submenu-section.open .site-header__navigation-submenu { display: block; } /* Top navigation mobile styles */ @media (max-width: 1023px) { .site-header__navigation-collapsible--collapse { height: 0; overflow-y: hidden; } .site-header__navigation-submenu-section .site-header__navigation-submenu { padding: 0 1rem 0.5rem 1.5rem; display: block; top: 30px !important; left: 0 !important; } .site-header__navigation-item, .site-header__navigation-submenu-section .site-header__navigation-submenu .site-header__navigation-submenu-item-link .site-header__navigation-submenu-item-link-text { font-size: 18px; } .site-header { padding: 5px 12px; } .site-header-version { display: none; } .site-footer__navigation { flex-direction: column; } .site-footer__links { flex-wrap: wrap; } .site-footer__link-group { margin-bottom: 1rem; } } /* Top navigation desktop styles */ @media (min-width: 1024px) { .site-header { -webkit-box-shadow: 0 2px 4px 0 var(--box-shadow-color); -moz-box-shadow: 0 2px 4px 0 var(--box-shadow-color); box-shadow: 0 2px 4px 0 var(--box-shadow-color); z-index: 2; } body.dark-theme { .site-header { -webkit-box-shadow: none; -moz-box-shadow: none; box-shadow: none; z-index: 2; } } @media (prefers-color-scheme: dark) { .site-header { -webkit-box-shadow: none; -moz-box-shadow: none; box-shadow: none; z-index: 2; } body.light-theme { .site-header { -webkit-box-shadow: 0 2px 4px 0 var(--box-shadow-color); -moz-box-shadow: 0 2px 4px 0 var(--box-shadow-color); box-shadow: 0 2px 4px 0 var(--box-shadow-color); z-index: 2; } } } /* Pushes the section headings to just below the top nav bar when a user navigates directly to section anchors. */ #content h2[id], #content h3[id], #content h4[id], #content h5[id] { padding-top: 60px; } #content h2[id] { /* Little extra room above h2s */ margin-top: -1em; } #content h3[id], #content h4[id], #content h5[id] { margin-top: -60px; } .site-header__navigation { flex-direction: row; } .site-header__navigation-button { display: none; } .site-header__navigation-items { flex-direction: row; align-items: center; float: right; width: auto; padding-top: 0; } .site-header__navigation-item { width: auto; } .site-header__navigation-item .site-header__navigation-link { padding: 15px 18px; } .site-header__navigation-item:last-of-type .site-header__navigation-link { padding-right: 0; } .site-header__navigation-link--button { padding: 6px 12px; } .site-header__navigation-collapsible { height: auto; } .site-header__navigation-submenu-section .site-header__navigation-submenu { position: absolute; border: 1px solid #9a9a9a; border-radius: 3px; } .site-header__navigation-submenu-section:hover .site-header__navigation-submenu { display: block; } /* Pushes the section headings to just below the top nav bar when a user navigates directly to section anchors. It doesn't work if you try to apply the padding and margin to the `h` elements directly. */ .chapter a[name], .chapter .anchor { padding-top: 60px; margin-top: -60px; text-decoration: none; border: none; display: inline-block; } } /* Side Navigation styles */ /* Docs Navigation */ .docs-navigation { border-right: 1px solid var(--various-border-color); } .docs-navigation .search-container { display: none; margin-bottom: 1rem; } .docs-navigation a { color: var(--text-color); display: block; font-size: .95rem; position: relative; } .docs-navigation a:focus { outline: none; } .docs-navigation a:hover { color: #35c1e4; text-decoration: none; } .docs-navigation a code { color: var(--text-color); overflow-wrap: break-word; padding: 0; word-break: break-all; } .docs-navigation a.active { color: #06A0CE; outline: 0; border: none; -moz-outline-style: none; } .docs-navigation a.active:hover { color: #35c1e4; text-decoration: underline; } .docs-navigation ul { list-style-type: none; margin: 0; padding: 0; } .docs-navigation li>ul>li a { font-size: 14px; color: #7d7d7d; } .docs-navigation ul:last-of-type { margin-bottom: 0; } .docs-navigation li { margin-top: 0.3334em; line-height: 1.3334; } .docs-navigation li:last-of-type { margin-bottom: 0; } .docs-navigation .nav-dropdown:before { content: '\2023'; font-size: 28px; position: absolute; margin-left: -14px; margin-top: -8px; } .docs-navigation .nav-dropdown.expanded:before { transform: rotate(90deg); } .docs-navigation>ul ul, .docs-navigation>ul ul ul { display: none; height: 0; margin-left: 1rem; } .docs-navigation>ul ul:target, .docs-navigation>ul ul:target ul, .docs-navigation>ul .nav-dropdown.expanded~ul { display: block; height: auto; } .docs-navigation h3 { font-size: .95rem; font-weight: 600; line-height: 1.5; margin: 1.5em 0 0; } .docs-navigation .docs-home-link { position: relative; } @media screen and (min-width: 45rem) { .main-content { display: flex; } } /* User guide navigation appears for desktops */ @media screen and (min-width: 64rem) { .docs-navigation { flex: 0 0 auto; width: 13.75rem; } .main-content>.appendix, .main-content>.book, .main-content>.chapter { flex: 0 0 auto; margin: 0 auto; } } /** * For mobile devices, we show navigation at bottom of page. * * This is the simplest solution to this issue. */ @media not screen and (min-width: 64rem) { /* Repeat the class twice to prioritize our mobile classes! */ .content.content { /* Make the height equal to the real height of content */ overflow: visible; } .main-content { /* Main content show first */ flex-direction: column-reverse; } .docs-navigation.docs-navigation { /* Fill the main container */ width: 100%; /* Don't clip the navigation container */ overflow: visible; } } /* Userguide Meta */ .chapter-meta { float: right; text-align: right; } .chapter-meta .edit-link { color: #999; font-size: 0.9em; padding-right: 3px; } .chapter-meta .edit-link svg { margin-right: 1px; } /* Clever use of RTL to fill in all stars to left of hover position */ .rating { direction: rtl; } .rating>.star { cursor: pointer; display: table-cell; padding: 3px; } .rating>.star:hover>svg>g, .rating>.star:hover~.star>svg>g, .rating>.star.selected>svg>g, .rating>.star.selected~.star>svg>g { fill: #999; } /* Footer styles */ .site-footer {} .site-footer__navigation { display: flex; padding: 30px 12px; max-width: 62.5rem; margin: 0 auto; padding-left: 5rem; } @media not screen and (min-width: 64rem) { .site-footer__navigation { /* same to nav.docs-navigation for mobiles */ padding: 20px 20px 20px 26px; } } .site-footer__links { display: flex; flex: 1 1 auto; } .site-footer__links .site-footer__links-list { list-style-type: none; margin: 0; } .site-footer__links .site-footer__links-list a { color: var(--footer-other-text-color); } .site-footer__link-group { flex: 1 1 auto; flex-basis: 175px; } .site-footer__link-group header { color: var(--text-color); } .site-footer__subscribe-newsletter .newsletter-form__header h5 { color: var(--text-color); margin-top: 0; } .site-footer__subscribe-newsletter p { font-size: 0.875rem; margin: 2px 0 0 2px; opacity: 0.7; } .site-footer__subscribe-newsletter .disclaimer { color: var(--footer-other-text-color); font-size: 0.75rem; opacity: 0.55; } .site-footer__subscribe-newsletter .newsletter-form { padding-top: 6px; display: flex; justify-content: flex-start; } .site-footer__subscribe-newsletter .email, .site-footer__subscribe-newsletter .submit { height: 40px; } .site-footer__subscribe-newsletter .email { line-height: 40px; width: 250px; color: #1DA2BD; font-size: 16px; padding-left: 20px; border-top-left-radius: 4px; border-bottom-left-radius: 4px; border: 1px solid var(--footer-form-color); } .site-footer__subscribe-newsletter .submit { font-family: inherit; font-size: inherit; line-height: inherit; width: 100px; background-color: #1BA8CB; color: #fff; font-weight: 500; border-top-right-radius: 4px; border-bottom-right-radius: 4px; border-style: none; cursor: pointer; transition: all .3s ease; } /* Secondary footer (below) */ .site-footer-secondary { background-color: var(--footer-white-color); border-top: 1px solid var(--various-border-color); width: 100%; z-index: 1; } body.dark-theme { .site-footer-secondary { background-color: var(--footer-white-color); border-top: none; width: 100%; z-index: 1; } } @media (prefers-color-scheme: dark) { .site-footer-secondary { background-color: var(--footer-white-color); border-top: none; width: 100%; z-index: 1; } body.light-theme { .site-footer-secondary { background-color: var(--footer-white-color); border-top: 1px solid var(--various-border-color); width: 100%; z-index: 1; } } } .site-footer-secondary__contents { display: flex; align-items: center; justify-content: space-between; max-width: 75rem; margin-left: auto; margin-right: auto; font-size: 0.875rem; padding: 0.5rem 0.75rem; } /* * 1. Value is the largest computed width among 'site-footer__copy' and 'site-footer__links'. */ .site-footer__copy, .site-footer__secondary-links { flex-grow: 0; flex-basis: 280px; /* 1. */ } /* * 1. 'flex-shrink: 1' is applied to the element with the smallest computed width among * 'site-footer__copy' and 'site-footer__links'. */ .site-footer__copy { flex-shrink: 1; /* 1. */ } .site-footer__logo { flex: 0 0 auto; margin-right: 10px; margin-left: 10px; } .site-footer__logo svg { width: 35px; height: 35px; } /* * 1. 'flex-shrink: 0' is applied to the element with the largest computed width among * 'site-footer__copy' and 'site-footer__links'. */ .site-footer__secondary-links { flex-shrink: 0; /* 1 */ text-align: right; white-space: nowrap; } .site-footer-secondary a { color: #999; } .site-footer-secondary__links a:not(:last-child) { padding-right: 10px; } .site-footer-secondary__links a:not(:first-child) { padding-left: 10px; } @media all and (max-width: 29.99rem) { .site-footer__rights, .site-footer-secondary__links { display: none; } .site-footer__logo { order: 1; text-align: left; } .site-footer__copy { order: 2; text-align: right; } } /* Avoid the footer taking up much of the screen on short displays */ @media all and (max-height: 56.25rem) { .site-footer__navigation { margin: 1.5rem auto 0 auto; padding-top: 0; padding-bottom: 0; } } @media screen and (min-width: 84.375rem) { .ui-logos .ui-logo { box-shadow: 0 6px 15px 1px rgba(0, 0, 0, 0.56); } } /* User Manual Home */ .technology-logos, .ui-logos { display: flex; flex-direction: row; flex-wrap: wrap; justify-content: space-around; } .technology-logo, .ui-logo { flex: 0 1 auto; } .ui-logo { width: 224px; height: 135px; margin: 12px; } /* Samples download button */ .download { display: flex; } .download a { border-style: solid; border-width: 1px; text-decoration: none; padding: 5px; display: block; width: 10em; margin: 5px; } .download ul { list-style: none; list-style-type: none; } .download li { float: right; } .docs-navigation { width: 18rem; padding: 20px 20px 20px 26px; background: var(--nav-color); overflow-y: scroll; overflow-x: auto; } .layout { display: flex; flex-direction: column; overflow: hidden; height: 100vh; } .main-content { overflow-y: auto; overflow-x: auto; display: flex; } .content { flex: 1 1 auto; overflow: auto; padding-left: 0; padding-right: 0; } .content .chapter { padding: 2rem 2.4rem; } #toc a:active { font-weight: 500; } .site-header { margin-bottom: 1rem; } .site-header__navigation-submenu-item { padding: 2px 0; } .site-footer { background-color: var(--footer-color); padding: 20px 0 40px 0; border-top: 1px solid var(--various-border-color); } #header { margin-left: 0; } #header>h1:first-child { margin-bottom: 40px; } @media screen and (min-width: 64rem) { #header { margin-bottom: 20px; } .site-header { margin-bottom: 0; z-index: 2; } .site-header__navigation-header { margin-top: -7px; } .site-header__navigation-submenu-section:after { content: '\2023'; font-size: 28px; position: absolute; transform: rotate(90deg); margin-right: 10px; top: 5px; right: -7px; } .site-footer__navigation { flex-wrap: wrap; } .site-footer__link-group { flex: 1 1 auto; } .site-footer__links { margin-bottom: 1rem; } } @media screen and (min-width: 75rem) { .content .chapter { box-sizing: content-box; } #content { padding-right: 260px; margin: 0; } /* #toc here must be referenced as #header #toc since we don't want to change single page #toc */ #header #toc { position: fixed; margin: 0 auto; padding-bottom: 0; right: 0; top: 65px; width: 260px; z-index: 1; overflow: auto; border-radius: 0 0 5px 0; max-height: calc(100% - 118px); margin-right: 15px; } #header #toctitle { margin-top: 1.3em; } #header #toc>ul { /* margin-left have to increase if you change border thickness of active toc item */ margin-left: 1px; border-left: 1px solid #666; margin-bottom: 0; padding-right: 10px; padding-bottom: 0.5rem; background-color: var(--white-color); } #header #toc>ul>li, #toc>ul>li:last-of-type { padding: 0.5rem 0; margin: 0; } #header #toc a { padding-left: 10px; font-weight: 400; color: var(--text-color); font-size: .95rem; display: inline-block; } #header #toc a.active { font-weight: 500; border-left: 3px solid #01303a; margin-left: -2px; padding-left: 9px; } .site-footer__navigation { flex-wrap: wrap; margin-left: auto; padding-left: 3rem; } .site-footer__link-group { flex: 0.15 1 auto; } .site-footer__subscribe-newsletter { /* A fix so subscribe disclaimer does not go under long ToC */ max-width: calc(100% - 17rem); } } @media screen and (min-width: 80rem) { .site-footer__subscribe-newsletter { max-height: none; } } @media screen and (min-width: 100rem) { .content .chapter { max-width: 60.5rem; } #header { margin: 0 auto; } #content { padding-right: 0; margin: 0 auto; } #header #toc { right: initial; margin-left: 62.5rem; } .site-footer__navigation { padding-left: 0; } .site-footer__link-group { flex: 0.2 1 auto; } } @media screen and (min-width: 112rem) { .content .chapter { max-width: 62.5rem; margin: 0 auto; padding-right: 3.5rem; position: relative; left: -130px; } #header #toc { right: initial; margin-left: 64.5rem; } .site-footer__link-group { flex: 0.2 1 auto; } } @supports (-moz-appearance:meterbar) and (background-blend-mode:difference, normal) { /* Firefox only */ .site-header__navigation-submenu-section:after { top: 2px; right: -4px; } } /* Added dark mode and other items for outdated Prettify.css */ code[data-lang="text"] .pln, code[data-lang="text"] .str, code[data-lang="text"] .kwd, code[data-lang="text"] .com, code[data-lang="text"] .typ, code[data-lang="text"] .lit, code[data-lang="text"] .pun, code[data-lang="text"] .opn, code[data-lang="text"] .clo, code[data-lang="text"] .tag, code[data-lang="text"] .atn, code[data-lang="text"] .atv, code[data-lang="text"] .dec, code[data-lang="text"] .var, code[data-lang="text"] .fun { color: #000; } body.dark-theme { code[data-lang="text"] .pln, code[data-lang="text"] .str, code[data-lang="text"] .kwd, code[data-lang="text"] .com, code[data-lang="text"] .typ, code[data-lang="text"] .lit, code[data-lang="text"] .pun, code[data-lang="text"] .opn, code[data-lang="text"] .clo, code[data-lang="text"] .tag, code[data-lang="text"] .atn, code[data-lang="text"] .atv, code[data-lang="text"] .dec, code[data-lang="text"] .var, code[data-lang="text"] .fun { color: #fff !important; } .com { color: #909090 !important; } .str, .tag { color: #90a959 !important; } .kwd, .atv { color: #d28445 !important; } .typ { color: #f4bf75 !important; } .lit, .atn { color: #6a9fb5 !important; } .pun, .pln, .opn, .clo { color: #d0d0d0 !important; } .dec, .var { color: #aa759f !important; } li.L1, li.L3, li.L5, li.L7, li.L9 { background: #111 !important; } } @media (prefers-color-scheme: dark) { code[data-lang="text"] .pln, code[data-lang="text"] .str, code[data-lang="text"] .kwd, code[data-lang="text"] .com, code[data-lang="text"] .typ, code[data-lang="text"] .lit, code[data-lang="text"] .pun, code[data-lang="text"] .opn, code[data-lang="text"] .clo, code[data-lang="text"] .tag, code[data-lang="text"] .atn, code[data-lang="text"] .atv, code[data-lang="text"] .dec, code[data-lang="text"] .var, code[data-lang="text"] .fun { color: #fff !important; } .com { color: #909090 !important; } .str, .tag { color: #90a959 !important; } .kwd, .atv { color: #d28445 !important; } .typ { color: #f4bf75 !important; } .lit, .atn { color: #6a9fb5 !important; } .pun, .pln, .opn, .clo { color: #d0d0d0 !important; } .dec, .var { color: #aa759f !important; } li.L1, li.L3, li.L5, li.L7, li.L9 { background: #111 !important; } body.light-theme { code[data-lang="text"] .pln, code[data-lang="text"] .str, code[data-lang="text"] .kwd, code[data-lang="text"] .com, code[data-lang="text"] .typ, code[data-lang="text"] .lit, code[data-lang="text"] .pun, code[data-lang="text"] .opn, code[data-lang="text"] .clo, code[data-lang="text"] .tag, code[data-lang="text"] .atn, code[data-lang="text"] .atv, code[data-lang="text"] .dec, code[data-lang="text"] .var, code[data-lang="text"] .fun { color: #000; } .pln { color: #000 !important;; } .com { color: #800 !important;; } .str, .tag { color: #080 !important;; } .kwd, .atv { color: #008 !important;; } .typ { color: #606 !important;; } .lit, .atn { color: #066 !important;; } .pun, .opn, .clo { color: #660 !important;; } .dec, .var { color: #606 !important;; } li.L1, li.L3, li.L5, li.L7, li.L9 { background: #eee; } } } /* DPE University button*/ /* CSS */ .badge-wrapper { padding-top: 0px; padding-bottom: 20px; a { text-decoration: none; } a:link { text-decoration: none; } a:visited { text-decoration: none; } a:hover { text-decoration: none; } a:active { text-decoration: none; } } .badge { background-color: var(--black-color); height: 24px; border-radius: 12px; border-color: var(--black-color); border-style: solid; border-width: 1px; padding: 5px; a { color: var(--gradle-blue); } } .badge-type { border-radius: 8px; margin-right: 10px; padding-left: 10px; padding-right: 10px; } .badge-text { color: var(--white-color); } .button--blue { color: white; border-color: transparent; &:hover { color: white; } } .button--blue { background: var(--gradle-blue); background: linear-gradient(var(--button-gradient-angle), var(--gradle-blue) 0%, var(--gradle-blue-lite) 100%); &:hover { background: var(--gradle-blue-lite); } } /* Custom Download button*/ /* CSS */ .button-9 { appearance: button; backface-visibility: hidden; background-color: #209BC4; border-radius: 6px; border-width: 0; box-shadow: rgba(50, 50, 93, .1) 0 0 0 1px inset, rgba(50, 50, 93, .1) 0 2px 5px 0, rgba(0, 0, 0, .07) 0 1px 1px 0; box-sizing: border-box; color: #fff; cursor: pointer; font-family: -apple-system, system-ui, "Segoe UI", Roboto, "Helvetica Neue", Ubuntu, sans-serif; font-size: 100%; height: 44px; line-height: 1.15; margin: 12px 12px 12px 0px; outline: none; overflow: hidden; padding: 0 25px; position: relative; text-align: center; text-transform: none; transform: translateZ(0); transition: all .2s, box-shadow .08s ease-in; user-select: none; -webkit-user-select: none; touch-action: manipulation; width: 25%; } .button-9:disabled { cursor: default; } .button-9:focus { box-shadow: rgba(50, 50, 93, .1) 0 0 0 1px inset, rgba(50, 50, 93, .2) 0 6px 15px 0, rgba(0, 0, 0, .1) 0 2px 2px 0, rgba(50, 151, 211, .3) 0 0 0 4px; } .button-9-sect { padding-bottom: 1.25em; } /* Theme toggle switch button */ /* Switch */ .switch { position: relative; display: inline-block; width: 60px; height: 34px; align-self: center; } .switch input { opacity: 0; width: 0; height: 0; } .slider { position: absolute; cursor: pointer; top: 0; left: 0; right: 0; bottom: 0; background-color: #ccc; -webkit-transition: 0.4s; transition: 0.4s; } .slider:before { position: absolute; content: ""; height: 26px; width: 26px; left: 4px; bottom: 4px; background-color: white; -webkit-transition: 0.4s; transition: 0.4s; } input:checked+.slider { background-color: #2196f3; } input:checked+.slider:before { -webkit-transform: translateX(26px); -ms-transform: translateX(26px); transform: translateX(26px); } /* Rounded sliders */ .slider { border-radius: 30px; } .slider:before { border-radius: 50%; } </style> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/4.7.0/css/font-awesome.min.css"> <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/prettify/r298/prettify.min.css"> <meta name="adoc-src-path" content="platforms/native/native_software.adoc"> <link crossorigin href="//assets.gradle.com" rel="preconnect"> <link href="https://fonts.googleapis.com/css?family=Inconsolata:400,700" rel="stylesheet"/> <style type="text/css">.multi-language-selector .language-option[data-lang='groovy'], .exampleblock[data-lang=groovy] > .content .title { background-image: url('data:image/svg+xml;base64,PHN2Zw0KICAgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIg0KICAgd2lkdGg9IjYxNC4wNjA4NSINCiAgIGhlaWdodD0iMzAzLjU5ODYiDQogICB2ZXJzaW9uPSIxLjEiPg0KICA8Zw0KICAgICB0cmFuc2Zvcm09InRyYW5zbGF0ZSgtMzUuMzk2NTk5LC0zMC41NTgxOTYpIj4NCiAgICA8cGF0aA0KICAgICAgIGQ9Im0gMTU0Ljk3Njg3LDMzMi42OTE2MiBjIDAsLTAuODA1ODcgMTAuODMxMjMsLTE4LjYyMTcyIDI0LjA2OTQsLTM5LjU5MDc2IDEzLjIzODE5LC0yMC45NjkwNSAyMi42NjA1NywtMzguNjIwNjYgMjAuOTM4NjcsLTM5LjIyNTc3IC0xLjcyMTkxLC0wLjYwNTEgLTcuNjc5OTIsMC40ODU2NyAtMTMuMjQwMDIsMi40MjM5MyAtMTYuNzQ1MjQsNS44Mzc0MyAtMjAuMTg2MDUsNC4yOTAxNiAtMzIuNjkzMDgsLTE0LjcwMTU1IC0xMy41MzI2NSwtMjAuNTQ5MDYgLTE0LjAxNzI0LC0yMi42Njk4MyAtNi45NjE1OCwtMzAuNDY2MjQgNC42MDg3NiwtNS4wOTI1NiA0LjMzMTU5LC02LjI3OTY3IC0zLjIzMTksLTEzLjg0MzE2IC00LjU1MDA5LC00LjU1MDEgLTguMjcyODksLTkuNjQzMDkgLTguMjcyODksLTExLjMxNzc2IDAsLTIuODE2NzkgLTMwLjk5MTQ1LC0xNS41ODkzMyAtNzkuOTg5NDk2LC0zMi45NjYxNSAtMTEuMTA5NjYsLTMuOTM5OTcgLTIwLjE5OTM3NSwtNy44MjkyOCAtMjAuMTk5Mzc1LC04LjY0MjkxIDAsLTAuODEzNjYgMjMuNDcwNzM4LC0xLjAwNDc2IDUyLjE1NzE5MSwtMC40MjQ2OSBsIDUyLjE1NzIxLDEuMDU0NjYgNS4wOTEyNywtOC4wMzAwMSBjIDIxLjUxNjQ0LC0zMy45MzU5MiA1NC4wMDk1MiwtNjQuNTg4MjEyIDY4LjQ2NzA1LC02NC41ODgyMTIgMy4wMTA2LDAgOS4xMjE0MSwyLjg2OTE4IDEzLjU3OTUzLDYuMzc1OTQ1IDcuMjU5NDYsNS43MTAyODMgOC4yNTY1LDkuMjQ4NjMyIDkuNTQ5OTQsMzMuODkxOTY3IDAuNzk0MywxNS4xMzM4MiAyLjQyNDIyLDI4LjQ5NjAxIDMuNjIxOTgsMjkuNjkzNzkgMS4xOTc3NSwxLjE5Nzc2IDQuOTk3NjksLTAuMzc0MjUgOC40NDQzMSwtMy40OTMzOSA0LjQwMTQsLTMuOTgzMjMgOS4wMzQ4NCwtNS4wNjMxMyAxNS41Njc2MSwtMy42MjgzIDYuNzY3NTYsMS40ODY0MSAxMC42MjcxLDAuNDY4OTUgMTQuMTY5MzgsLTMuNzM1NDMgNS4zMTM2LC02LjMwNjY2IDMxLjkwNTk2LC00OC45MzcyMDEgMzEuOTA1OTYsLTUxLjE0ODc0NCAwLC0wLjc1MTU4OCA1LjI2NTA5LC05Ljc1NzMwNiAxMS43MDAyMywtMjAuMDEyNzAzIDYuNDM1MDksLTEwLjI1NTM5NyAxMy44NDY2NCwtMjIuMDgwNjMxIDE2LjQ3MDA3LC0yNi4yNzgyODMgNC42NjU1OCwtNy40NjUyMDEgNS4zOTY2LC02LjU4MTczNSAzMy40MjY5Miw0MC4zOTg3MzYgMjguOTQxMjEsNDguNTA3MTY0IDQ0LjUxNzY3LDY2LjQwNjU1NCA1Mi4zMTU3LDYwLjExNzYzNCA1LjQ0MiwtNC4zODg4OSAzNC4wMDA1NSwtNC42Mzc5NCA0MS45ODI0NiwtMC4zNjYxNCA0LjUzNjY1LDIuNDI3OTMgNy40MTkxNiwyLjM5NjEgOS45MjQ4NCwtMC4xMDk2MiA1LjIwMDA3LC01LjIwMDA2IDE3LjY0OTgyLC00LjI5NDM3IDIwLjkwNDEyLDEuNTIwNzggMi41NjM5Myw0LjU4MTQ2IDMuMjE3ODQsNC41ODE0NiA3LjAyMDE0LDAgMi4zMDYwNiwtMi43Nzg2NyA5LjEzNjE5LC01LjA1MjA4IDE1LjE3ODAzLC01LjA1MjA4IDguNTM4ODQsMCAxMS43OTMzNiwxLjc3MzY3IDE0LjYxNDAzLDcuOTY0MzcgbCAzLjYyODgxLDcuOTY0MzYgNTYuMDkyMDMsLTEuOTg1OCBjIDMwLjg1MDYyLC0xLjA5MjIyIDU2LjA5MjA0LC0xLjI4Njg4IDU2LjA5MjA0LC0wLjQzMjU1IDAsMC44NTQyNyAtMjIuOTA2MDgsMTAuMDcxOTUgLTUwLjkwMjQxLDIwLjQ4MzcxIC0yNy45OTYzMiwxMC40MTE3MiAtNTEuMzY3LDE5LjI0MzA1IC01MS45MzQ4NCwxOS42MjUxMiAtMC41Njc4NSwwLjM4MjA3IDAuNjk4NDcsOS40OTI3MyAyLjgxNDA1LDIwLjI0NTg4IDUuNTA0NTcsMjcuOTc5MTcgMS45MTQ1OCw0Ni42MjU4OSAtMTEuOTI2MjksNjEuOTQ2MDQgLTYuMjA5LDYuODcyNjMgLTE2LjI4MzM4LDE0LjE0Mzk1IC0yMi4zODc1MywxNi4xNTg0OSAtNi4xMDQxNSwyLjAxNDU0IC0xMS4wOTg0NCw0LjM4NjE0IC0xMS4wOTg0NCw1LjI3MDE5IDAsMC44ODQwNiA2LjUxNTI1LDExLjY3ODkzIDE0LjQ3ODM1LDIzLjk4ODU5IDcuOTYzMDksMTIuMzA5NjkgMTMuMjgyOCwyMi4zODEyNSAxMS44MjE1MiwyMi4zODEyNSAtMi4zODUwNCwwIC02MC40Njk4NywtMjIuNDQyMzggLTE1MC43ODg5OCwtNTguMjYwNyAtMTcuODA5LC03LjA2MjU4IC0zNC4wMjY4MywtMTIuODQxMDkgLTM2LjAzOTYxLC0xMi44NDEwOSAtMy43NTM2MywwIC0zNi4xNjY5LDEyLjI4NjYyIC0xMzEuMjI0MjMsNDkuNzQyMDYgLTU1LjEyNTI1LDIxLjcyMTAzIC01Ny4yOTIxNywyMi40NzM0OCAtNTcuMjkyMTcsMTkuODk0NTEgeiBtIDExMy4xMTY0OCwtNTEuMjUyNjUgYyAyOS4zMjk0OSwtMTEuMzk1MDYgNTguNDE2NTcsLTIyLjUzMDggNjQuNjM3OTgsLTI0Ljc0NjA3IDEwLjcwMDY4LC0zLjgxMDE5IDE0LjI3OTE4LC0yLjg1NDkzIDY2LjI1Mzk0LDE3LjY4NjM0IDMwLjIxODI1LDExLjk0Mjc0IDYwLjAzMjUyLDIzLjU3NTg3IDY2LjI1MzkyLDI1Ljg1MTM0IDYuMjIxNDEsMi4yNzU1MiAxOS4wNDMxNyw3LjIyMDU5IDI4LjQ5Mjc1LDEwLjk4OTA4IDEwLjc3NTAzLDQuMjk3MDQgMTYuMjgyNTEsNS4zMzE2NiAxNC43NzEwOCwyLjc3NDg0IC0xNi44ODM3LC0yOC41NjExMyAtMTcuMzk5OCwtMjkuMDM3MTYgLTI5LjEwMDgzLC0yNi44NDIwNSAtMTQuMTEzNjEsMi42NDc3MiAtMjIuODc4OTcsLTAuMDY4NSAtMjcuMzgzNjksLTguNDg1NTQgLTIuOTIxMTIsLTUuNDU4MTYgLTIuMDI5NDQsLTguMTI3NTkgNS4yNTQ0MiwtMTUuNzMwMzEgMTAuODQ4ODcsLTExLjMyMzc3IDkuMTQ0NTcsLTIxLjc0MTQ0IC00Ljg0NDI5LC0yOS42MTA5OSAtNS4zNjc2NCwtMy4wMTk1OSAtMTIuMTQwNTksLTEwLjQ4MzcyIC0xNS4wNTEwMiwtMTYuNTg2OTcgbCAtNS4yOTE2OSwtMTEuMDk2ODIgLTExLjM0NTUxLDcuNjk5MjggYyAtMTMuOTQ0NTgsOS40NjMwNCAtMzAuOTUwNjIsOS45NTA2MyAtNDUuMTQ3NjQsMS4yOTQ0OCBsIC0xMC40NjQ4OCwtNi4zODA2NSAtMTIuMTU4NDEsOC4yNjI4NCBjIC0xMi4xNzQ2Miw4LjI3Mzg2IC0yNi4xOTEwOCw5LjM0MjggLTQwLjQzNzUyLDMuMDgzOTIgLTMuOTI0OTgsLTEuNzI0MzkgLTUuNjU1ODMsLTEuMDU0MTUgLTUuNjU1ODMsMi4xOTAwOCAwLDIuNTcxMTggLTMuNzA0MjksNi4zNjI2NSAtOC4yMzE4MSw4LjQyNTUzIC0xMy41NzQyLDYuMTg0NzkgLTI2LjgyMTA3LDQuNTQyNDcgLTM1LjgwMjI5LC00LjQzODc1IGwgLTguMTg5NDQsLTguMTg5NDQgLTYuNjA5ODIsOC40MDMwMyBjIC0zLjYzNTM5LDQuNjIxNjYgLTEyLjA0OTUyLDExLjgzNjk4IC0xOC42OTgwNSwxNi4wMzM5OCAtOC4yMjk2NSw1LjE5NTE4IC0xOC40MTc0MSwxNy44NzE4MiAtMzEuOTE2NCwzOS43MTM2MSAtMTAuOTA1NDksMTcuNjQ1NDYgLTE5LjgyODE2LDMyLjk4MDQyIC0xOS44MjgxNiwzNC4wNzc3NiAwLDEuMDk3MyA4LjM2MjU1LC0xLjUyNzM2IDE4LjU4MzQyLC01LjgzMjU5IDEwLjIyMDg5LC00LjMwNTIxIDQyLjU4MDI4LC0xNy4xNTA4NyA3MS45MDk3NywtMjguNTQ1OTMgeiBtIDI0OC43NjcyOSwtMTIuMjU4NDYgYyAyMi4yNTU1NywtMTIuNTA4MzMgMjcuNDE0MjQsLTM1LjY0ODA4IDE3LjU3Njg1LC03OC44NDMxOCAtOC4yMjE0LC0zNi4wOTk2MSAtMTIuMzI1NSwtNDcuOTEzMjcgLTE3LjE5NDk0LC00OS40OTU5NyAtMy4zNjkwMiwtMS4wOTUwMyAtMy44ODY3NCwwLjEwNjk5IC0xLjk4ODU4LDQuNjE2MzUgMTIuMzE1MTYsMjkuMjU3NzEgMTIuOTk5NjMsNDMuOTQ2NjIgMi4yNDAyMiw0OC4wNzU0MSAtNy4zOTE1MSwyLjgzNjQyIC0xNS4yMzIzOSwtNy43OTA3NSAtMjEuMzk5MDIsLTI5LjAwMzI2IC00Ljc3NTEyLC0xNi40MjU4NyAtOS43Njg2MSwtMjMuODI4MzcgLTEzLjUzMzg3LC0yMC4wNjMxMSAtMC45MDE1NywwLjkwMTYgMC42Nzg0OCw2LjEyMTE3IDMuNTExMjQsMTEuNTk5MTMgMi44MzI3Myw1LjQ3NzkgNi43MTcyMSwyMS45NzQ1NSA4LjYzMjE3LDM2LjY1OTIgMS45MTQ5NywxNC42ODQ2MiA1LjYxMzg1LDMwLjA2MDczIDguMjE5NzMsMzQuMTY5MTIgNi43NzE5OCwxMC42NzY2MSAxNy41NTEyOCw4LjEwMzYgMjQuNTIzODIsLTUuODUzODQgNi44OTM3MywtMTMuNzk5NzUgNy42NzI4NCwtNC42MDc4MSAwLjk2OTMsMTEuNDM2MDIgLTYuOTYwNzQsMTYuNjU5MzcgLTI3LjYzNDQyLDIxLjY1NDgxIC01MS41ODQxOCwxMi40NjQ0MiAtMy44MzMzLC0xLjQ3MDk2IC01LjEzMDM5LDAuMDUxNSAtNS4xMzAzOSw2LjAyMDk3IDAsNC4zOTQzMSAtMi45MzYxOCwxMS43MjI0NSAtNi41MjQ4OCwxNi4yODQ3IGwgLTYuNTI0ODgsOC4yOTUwNiA4Ljk0ODgxLDEuNTExMjMgYyAxNS40NDk0NSwyLjYwOTA5IDM2LjYzMzI4LC0wLjc3NjQyIDQ5LjI1ODYsLTcuODcyMjUgeiBtIC0zMjAuMzY2NSwtMjcuNTM3MzMgYyA0Ni40NTk2NSwtMTMuMzU0NSA1NC43NjE4OCwtMjguOTMwOTMgMzkuMzI4ODUsLTczLjc4NzgyIC0zLjU4MTg1LC0xMC40MTA3OSAtNi41MTI0MywtMjEuNjA5NzEgLTYuNTEyNDMsLTI0Ljg4NjU0IDAsLTExLjE1NzEyIC01LjYxMTUyLC02LjAwMTYxIC05LjgxNzEzLDkuMDE5NDMgLTUuNTYyMDMsMTkuODY1NjEgLTIyLjI5MTE1LDM2Ljc1MDUzIC0zNi4zNDUxNiwzNi42ODM2NCAtMTIuMjA1NDcsLTAuMDU4MiAtMTYuMTgyNTEsLTIuMjgwMDggLTIxLjIyMzc4LC0xMS44NTc2OCAtOS4wNDc0OCwtMTcuMTg4ODIgMC44MTQ2OSwtNDMuNTY3OTcgMjUuOTY5NTQsLTY5LjQ2MjcyIDE4LjQyNDMxLC0xOC45NjYzMDQgMjguNDg4OTMsLTIwLjY4Mzk2NSAyOC40ODg5MywtNC44NjIwNSAwLDI0LjY3MzIgLTE3LjAxMTM0LDYwLjk5NDcgLTI1Ljk3MzA5LDU1LjQ1NjA0IC00LjM4MjA1LC0yLjcwODI2IC0zLjY3MTM4LC0xNC42Njc1MiAxLjQxNzIyLC0yMy44NTAwOSA0LjMyNzM1LC03LjgwODgyIDMuNDQ4MTQsLTE5LjcwNzcxIC0xLjQ1NjIsLTE5LjcwNzcxIC01LjY4Njg5LDAgLTE2Ljk0NTQ3LDIwLjcxMTk2IC0xOC40MzMxOCwzMy45MTA3NCAtMS4zMTUxNSwxMS42NjgyNiAtMC40OTI4NiwxNC41MDU0NSA1LjA2NjUyLDE3LjQ4MDcyIDE5LjQ4MjQ0LDEwLjQyNjcgNDUuMDA1MzEsLTIxLjM5NTQ1IDQ2LjI5MDgzLC01Ny43MTU4NCAwLjY3NTA0LC0xOS4wNzMxODEgLTMuMDE2NzYsLTI0LjQ0MTEwNSAtMTQuNzc5MDYsLTIxLjQ4ODk1MSAtMTcuMTE4NzksNC4yOTY1NDMgLTYzLjIzNDgzLDYzLjc4NjY0MSAtNjMuMjM0ODMsODEuNTczNDYxIDAsMTMuOTEyOCA2Ljk4NzM3LDIzLjY5NzI4IDE5LjI4ODI3LDI3LjAwOTYgMjAuOTE0MTksNS42MzE2MiA0MS4xMzUzOSwtNC4zNzM4OSA1NS40NjMzLC0yNy40NDMzOCBsIDYuMDIxNzUsLTkuNjk1NzEgMC4wMTMyLDEzLjE3MjIzIGMgMC4wMTYyLDE5LjA3MzggLTEyLjQyNjE5LDI5LjEyNzQgLTUxLjY5ODE3LDQxLjc2NzkzIC05Ljc3NjQ5LDMuMTQ2OCAtMTguMTgzMzIsNi4wNTQ0MSAtMTguNjgxOCw2LjQ2MTM3IC0xLjgyMDU2LDEuNDg2MzIgMTYuNjg3MzksMjcuNDc1NzEgMTkuNTY2NDQsMjcuNDc1NzEgMS42MzI2MiwwIDExLjE5MTE1LC0yLjM2MzU5IDIxLjI0MTIzLC01LjI1MjM4IHogTSA0NzYuNDExLDIxNy45NjMwMSBjIDQuNjYzNDcsLTUuMTUzMSA1LjQ4NTUxLC0xMC43NTEwMyA0LjQ4NTc5LC0zMC41NDgyMyAtMS4wODczOSwtMjEuNTMzMzEgLTIuMjc3NDYsLTI1LjMzODUxIC0xMC42NjE0MywtMzQuMDg5NDkgLTE1LjE0ODgyLC0xNS44MTE5NCAtMzMuODYxMjMsLTExLjc3ODI4IC0yMi45MDgxOSw0LjkzODE0IDUuODIyNTYsOC44ODYzNyAxMi45MjU0LDcuMzY4NjQgMTAuNDE2NDEsLTIuMjI1ODEgLTEuOTk4NjQsLTcuNjQyNzYgMS43Mjk5OCwtNy44NDM1OCA4LjIyODM5LC0wLjQ0MzIyIDEyLjE5MzAxLDEzLjg4NTM3IDkuMTE1MzQsMzMuMTI2OTggLTUuMjk4NiwzMy4xMjY5OCAtOS44NjcxNiwwIC0xMi45NDE5NSwtNC4yMzE3NiAtMTkuMzczNTMsLTI2LjY2MzE4IC0yLjkzMDU5LC0xMC4yMjA4NyAtNi40OTk2NCwtMTguNTgzNDMgLTcuOTMxMjcsLTE4LjU4MzQzIC00Ljc2ODk5LDAgLTYuODkyODcsNC4yMDg3OCAtMy45MjcyMSw3Ljc4MjQgMS42MTA4OCwxLjk0MTEgNi4wNzIxOCwxNS44OTEyNyA5LjkxNDA0LDMxLjAwMDQxIDkuNjY5MDMsMzguMDI1OTYgMjMuMTc2NjYsNTEuMDQxNDUgMzcuMDU1NiwzNS43MDU0MyB6IG0gLTE4My43NzEyNSwwLjYwMzk1IGMgMS45ODk3OCwtMS4zMzUgMi44OTk3NSwtNy42NDg5MyAyLjA3ODY1LC0xNC40MjMgLTEuMzI0NDksLTEwLjkyNzAyIC0yLjA2NjYyLC0xMS43MjQxIC03Ljk3MjcsLTguNTYzMjcgLTguNDg3MzMsNC41NDIyNyAtMTcuNjA4MzksLTQuMDYzNTEgLTIwLjcwMjIyLC0xOS41MzI2IC0yLjM0NzA3LC0xMS43MzUzOCAtMy4wNjUyNiwtMTEuNTA0ODkgMTQuMDI1NzYsLTQuNTAxNDkgMi4xNDI4OCwwLjg3ODA4IDcuNTk2NzEsLTIuMTA0MDIgMTIuMTE5NjMsLTYuNjI2OTQgOC4yNzQwOCwtOC4yNzQwOCAxMC45OTgwMiwtMTguMjEyOTkgNC45OTE1NiwtMTguMjEyOTkgLTEuNzc3NTQsMCAtMy4yMzE5LDEuNDU0MzYgLTMuMjMxOSwzLjIzMTkgMCw0LjY0OTIzIC04Ljg0MjMxLDMuOTg5ODIgLTEwLjgzNDY1LC0wLjgwNzk3IC0xLjE2MjI0LC0yLjc5ODc5IC0zLjYzODA3LC0xLjgwNTkxIC04LjA1OTE1LDMuMjMxOSAtMy41MDk4NSwzLjk5OTQ4IC03Ljc5NjczLDcuMjcxNzggLTkuNTI2NDEsNy4yNzE3OCAtMS43Mjk2OSwwIC00LjA2NTYsLTMuMjcyMyAtNS4xOTA4OCwtNy4yNzE3OCAtMS45NzE5NSwtNy4wMDg1NiAtMi4yMTM2NiwtNy4wNTI3NyAtNi42NzczNywtMS4yMjE2OSAtMy45MTA2LDUuMTA4NTQgLTMuOTQ1NTcsNi43MzU4MyAtMC4yMjQ2MSwxMC40NTY2MSAzLjk0MDYyLDMuOTQwNjQgMTEuNDI2MTUsMzAuODcxMDIgMTEuNDI2MTUsNDEuMTA3NDQgMCwxMi43Mjg2NyAxNy41MjkzMywyMi43MzgzMiAyNy43NzgzLDE1Ljg2MjEgeiBtIDU4Ljk0MzA5LC0xNi44NzUzMSBjIDEyLjE0NTY3LC0xMi4xNDU2NyAxNS43NDQ1MiwtMzAuMzUxNDMgOS4xMjk0MywtNDYuMTgzNTcgLTUuMTcwMTYsLTEyLjM3Mzk3IC0xNC4xNDQ2NiwtMTcuMDA1MTYgLTI2Ljc5ODc4LC0xMy44MjkxOCAtOS40MDI2MywyLjM1OTkxIC0yMy43MjMxMSwyOS43NzY1OSAtMjMuNzczODcsNDUuNTE1MzYgLTAuMDc5MiwyNC41MjkwMiAyMy4yNTA1MywzMi42OTAwNSA0MS40NDMyMiwxNC40OTczOSB6IG0gLTIyLjA4MzQxLC0xOS40MzQwNyBjIC0zLjU1NTEsLTMuNTU1MSAtNi40MTc1NSwtMTAuNDYzMjggLTYuMzYxMDIsLTE1LjM1MTUzIDAuMDkzNCwtOC4wNzk2NSAwLjQ5MzE1LC04LjM3MzUgNC4zOTYxOSwtMy4yMzE5IDQuODI0NjQsNi4zNTU2OSAxMy4zOTc5Nyw3LjQ1NjY2IDE2LjY4MjQxLDIuMTQyMzIgMS4xOTQzMiwtMS45MzI0MSAwLjU1Mjk1LC01LjEzMjAyIC0xLjQyNTIsLTcuMTEwMTcgLTUuMDgxMzIsLTUuMDgxMzIgLTQuNDY1NjEsLTExLjk5OTYzIDEuMDY3OTIsLTExLjk5OTYzIDYuMTUxMzcsMCAxNC43MjY3OSwxMi41MTQ3NyAxNC43MjY3OSwyMS40OTE5MSAwLDYuNjA2NzQgLTEzLjQ0NDQsMjAuNTIyOCAtMTkuODI3MjQsMjAuNTIyOCAtMS41Mzc4NSwwIC01LjcwNDc2LC0yLjkwODcyIC05LjI1OTg1LC02LjQ2MzggeiBtIDg2LjM0ODk3LDE4LjU4MzQxIGMgMTMuNDEwNzQsLTE0LjYwMjYzIDEyLjEwMzc2LC0zNy4wOTggLTMuMDk4MjUsLTUzLjMyNjM0IC03Ljg1MDU3LC04LjM4MDYgLTI1LjI5Mjk4LC05LjgyNTUyIC0zMi40MzE4NSwtMi42ODY2NCAtNi41ODc2MSw2LjU4NzYxIC0xMy4xNjQ2NSwzMi40OTMwMyAtMTAuNzIxMjIsNDIuMjI4NDEgNS4yMTEyMiwyMC43NjMxOCAzMi40MDA0MSwyOC44NjY1MiA0Ni4yNTEzMiwxMy43ODQ1NyB6IG0gLTI3LjQ1NTY1LC0yMy42MTQ1MiBjIC01LjMwNjIzLC0zLjcxNjY0IC03LjEyOTQxLC04LjE0OTc0IC02Ljk3ODA2LC0xNi45Njc0NyAwLjE2OTM1LC05Ljg2MDMzIDAuNjg0MywtMTAuNzQ5ODEgMi45NjE0NSwtNS4xMTQxNSAzLjM0NTczLDguMjgwMzIgMTAuMzYyOTIsMTEuNDA3MzQgMTYuNTE4MTQsNy4zNjA5IDMuODE3NTMsLTIuNTA5NjMgMy42MzkyOSwtMy42OTU5NyAtMS4xMDEwNCwtNy4zMjkwNyAtNi4zMjE4OSwtNC44NDUyMyAtNy41NTUwOCwtMTEuNzAxOTEgLTIuMTA0NjUsLTExLjcwMTkxIDQuODczNjQsMCAyMi4zMDQwMiwxOS4wNjY2NiAyMi4zMDQwMiwyNC4zOTc3OCAwLDUuMjAzMTYgLTEyLjM3NzM5LDE0LjM4NTAzIC0xOS4zOTEzOSwxNC4zODUwMyAtMi43NjQwNSwwIC04LjI1NzksLTIuMjY0MDIgLTEyLjIwODQ3LC01LjAzMTExIHogbSAxODkuOTYyOTIsLTE0LjI4ODg3IDMzLjkzNDk1LC0xMi43MzY4MiAtMzYuMzU4ODgsLTAuMTMxMjUgYyAtMzIuNTM5MiwtMC4xMTczNiAtMzYuMzU0MjQsMC40NjMwNyAtMzYuMzE0NzUsNS41MjQ3NSAwLjA0MDEsNS4xMjc1NyAzLjMzMDczLDIwLjI4Mzk1IDQuMzcyNywyMC4xMzk2NyAwLjIzNzIyLC0wLjAzMjkgMTUuNzAxNzcsLTUuNzkxMjQgMzQuMzY1OTgsLTEyLjc5NjQ4IHogbSAtNDQzLjQ5MzQzLC0yLjI3OTMgMy40NjgyNSwtMTAuMjg3NjEgLTMwLjQ2Njg2LC0xLjAyNDA0IGMgLTE2Ljc1Njc0NCwtMC41NjMyMiAtMzAuNDYzNTg0LC0wLjEzMjEzIC0zMC40NTk1OCwwLjk1ODA0IDAuMDA1OCwxLjU5NTEzIDUyLjUwNjU3LDIyLjEwNzA3IDUzLjY2MTc0LDIwLjk2NTUyIDAuMTgwMzUsLTAuMTc4NCAxLjg4ODkyLC00Ljk1MzcyIDMuNzk2NDUsLTEwLjYxMTkxIHogbSAyMDguOTA5MiwtMzEuODg2OTUgYyA3LjE2NjY3LDEuMTQ2IDE1LjI0OTgxLDQuMDc5MjQgMTcuOTYyNTYsNi41MTgzNSA0LjIxMjc5LDMuNzg3ODMgNi4wNDUyOCwzLjUyOTY2IDEyLjU2MjA3LC0xLjc2OTg1IDQuMTk2NDMsLTMuNDEyNSA5LjY1MDI2LC02LjIwNDU3IDEyLjExOTYzLC02LjIwNDU3IDIuNDY5MzksMCA0LjQ4OTgyLC0wLjcxMzA4IDQuNDg5ODIsLTEuNTg0NjcgMCwtMy4wMDkxOCAtNDYuNTM5NTQsLTc5LjIxMjUyIC00OC4zMTQ0NywtNzkuMTA5NjEgLTIuMDg1LDAuMTIwODcyIC00OS43ODYwMyw4MC4wODc5OCAtNTEuMjU0NjQsODUuOTI0MzcgLTAuNjE2MzQsMi40NDk1MiAxLjMxODA0LDMuMzUzNzEgNS4wNzM2NCwyLjM3MTYgMy4zMzgzNiwtMC44NzMgNy45NTQxNiwwLjY4MzI2IDEwLjI1NzI3LDMuNDU4MzYgMy43MzU0LDQuNTAwODcgNS4yNjEwOCw0LjE0MjI5IDE0LjEzMDY4LC0zLjMyMDk3IDguNDI2NDcsLTcuMDkwNDEgMTEuOTMwOCwtOC4wNDg4IDIyLjk3MzQ0LC02LjI4MzAxIHoiDQogICAgICAgc3R5bGU9ImZpbGw6IzMzMzMzMztmaWxsLW9wYWNpdHk6MSIgLz4NCiAgICA8cGF0aA0KICAgICAgIHN0eWxlPSJmaWxsOiM2Mzk4YWE7ZmlsbC1vcGFjaXR5OjE7c3Ryb2tlOm5vbmUiDQogICAgICAgZD0ibSAzMDkuNTQ1NzksMTQwLjg3OTIyIGMgLTAuNTAwNzUsLTAuMjMzMTEgLTEuMTE4MDQsLTAuNzY3OTkgLTIuNTI3OCwtMi4xOTAzNSAtMS45MTE4OCwtMS45Mjg5NyAtMi42NzE4OCwtMi40OTAxMyAtNC4yNjEwOCwtMy4xNDYyOCAtMi4wODc5MSwtMC44NjIwNCAtNC4zNTQ5LC0xLjA5NDIzIC02LjQ4MjMxLC0wLjY2MzkxIC0xLjg5ODA4LDAuMzgzOTMgLTIuNDI0MzUsMC40MjUyNyAtMy4yODI0MiwwLjI1NzggLTEuNDMyMjQsLTAuMjc5NTMgLTEuOTQxNTcsLTEuMTQ5MjkgLTEuNTM1ODMsLTIuNjIyNzIgMC41MDU3MywtMS44MzY1NyA0LjMzNjkzLC04Ljk0MjU1IDEyLjAwODk5LC0yMi4yNzM4NyAxNS41ODM3LC0yNy4wNzg5ODggMzYuNTM2MjQsLTYxLjIyMDk2OCAzOC44NTA1NiwtNjMuMzA2NjYyIDAuMjU2MzEsLTAuMjMwOTk0IDAuMjY1LC0wLjIzMDk5NCAwLjUyMjQ4LDAgMS4zNzc2OCwxLjIzNTk3NiA5LjQ3NjIsMTMuNzI1ODg5IDIwLjU0MDM2LDMxLjY3ODI5OCAxNC45NjY5NiwyNC4yODUwMDQgMjcuNDExMDIsNDUuNjQzNzE0IDI3LjQxMTAyLDQ3LjA0NzcwNCAwLDAuODU3MjkgLTEuMzE2MDgsMS4zNzIxNSAtNC4wODU5MSwxLjU5ODQ1IC0zLjQ0MjI2LDAuMjgxMjQgLTcuNDI0NzgsMi4zMDE4OCAtMTIuODY4ODcsNi41MjkzNiAtMi41ODcxMiwyLjAwODk4IC0zLjY5MTI2LDIuNzU5MzMgLTQuOTUwNjIsMy4zNjQzOCAtMS4wNDkyOCwwLjUwNDExIC0xLjEzNjkyLDAuNTI0MzcgLTIuMjY4NTQsMC41MjQzNyAtMS4xMTM2OCwwIC0xLjIyNjYxLC0wLjAyNDkgLTIuMDk2MjMsLTAuNDYxMjggLTAuNTEyMTMsLTAuMjU3MDIgLTEuNTA0NjksLTAuOTQ5MyAtMi4yNDE1NSwtMS41NjM0MiAtMi4xNzg0OCwtMS44MTU2MSAtNC43OTkxOCwtMy4xMzYxNCAtOS4wNzE5NywtNC41NzEyNCAtNS40Mjk5NywtMS44MjM3NiAtMTEuMjQ0NTQsLTIuOTE4NCAtMTYuMTk1NTEsLTMuMDQ4OTYgLTMuOTA5MzQsLTAuMTAzMDggLTUuNzEyMDEsMC4yNDc5OCAtOC42NzYwMiwxLjY4OTYzIC0yLjQxOTg4LDEuMTc2OTggLTMuNTg2MjEsMi4wMTMxMSAtOS4xMjQ3NSw2LjU0MTQ1IC01LjYzMzc2LDQuNjA2MTcgLTcuNjM0NDIsNS41NjIwNSAtOS42NjQsNC42MTcyNSB6IiAvPg0KICAgIDxwYXRoDQogICAgICAgc3R5bGU9ImZpbGw6IzYzOThhYTtmaWxsLW9wYWNpdHk6MTtzdHJva2U6bm9uZSINCiAgICAgICBkPSJtIDEyOC42Mzc4NiwxNzAuNzM5IGMgLTEwLjE1OSwtMi45NjA3IC00NS41MDMxNzEsLTE2LjkxOTYyIC01MC40NTA5MjQsLTE5LjkyNTIzIC0wLjY4MjkxNiwtMC40MTQ4NCAtMC43MzgwOTgsLTAuNDc3ODcgLTAuNTQzMjA3LC0wLjYyMDM4IDEuMTMxNTYzLC0wLjgyNzQxIDEyLjMzNzk4MywtMS4yMzkwMSAyNS4wMDQwMzEsLTAuOTE4MzYgNS4wNTEzMSwwLjEyNzg4IDM1LjUwMTMyLDEuMTMzMjMgMzUuNTUwOSwxLjE3Mzc3IDAuMDk5NywwLjA4MTUgLTYuNTIxNjQsMTkuMjg4OCAtNy4wMzA1MSwyMC4zOTQzMyAtMC4yMTI1MSwwLjQ2MTcgLTAuNjUwNjMsMC40NDM2NyAtMi41MzAyOSwtMC4xMDQxMyB6IiAvPg0KICAgIDxwYXRoDQogICAgICAgc3R5bGU9ImZpbGw6IzYzOThhYTtmaWxsLW9wYWNpdHk6MTtzdHJva2U6bm9uZSINCiAgICAgICBkPSJtIDU0My42OTQxMywxNzUuMzEwNTUgYyAtMS4zODYyLC0yLjcxMjg3IC0zLjg4NzY5LC0xNC45NzA2NyAtMy45NjA3OCwtMTkuNDA4NTggLTAuMDI4NCwtMS43MjQyNCAwLjE4NjY3LC0yLjQyNzQxIDAuOTYwNiwtMy4xNDA4IDEuNzczNzgsLTEuNjM1MDEgNS4zNzkzOCwtMi4yMjMyIDE1LjI5MDE3LC0yLjQ5NDM0IDUuMDAzNDcsLTAuMTM2ODkgMjguMTAxOSwtMC4xNTc5NiA0NC40MTEyNywtMC4wNDA1IGwgMTEuNDI4NTksMC4wODIzIC0yNy41MTc3LDEwLjMxNDI3IGMgLTI1LjA5MjkyLDkuNDA1NCAtMzkuNjg0NzMsMTQuODQxMjYgLTQwLjIyNDkxLDE0Ljk4NDkgLTAuMTM1MTcsMC4wMzYgLTAuMjY5ODEsLTAuMDY3NCAtMC4zODcyNCwtMC4yOTcyMyBsIDAsMCB6IiAvPg0KICAgIDxwYXRoDQogICAgICAgc3R5bGU9ImZpbGw6IzYzOThhYTtmaWxsLW9wYWNpdHk6MTtzdHJva2U6bm9uZSINCiAgICAgICBkPSJtIDE3OC4wODgzNSwzMTUuNTE0MzMgYyAwLC0wLjc3MDc4IDMuMjY4OSwtNi41MzMxIDExLjU1Mzk1LC0yMC4zNjY5OCAxOS44NTExOCwtMzMuMTQ2MzEgMjguOTI3MTUsLTQ1LjE2MDEyIDQwLjA3MjkyLC01My4wNDQyOSA5Ljk3MTI3LC03LjA1MzM3IDE1LjMwMjc5LC0xMS45Mjk0IDIxLjI0NTM5LC0xOS40MzAzMyBsIDMuNjY0MDksLTQuNjI0OTIgNC45Mzk5LDQuODU2NTIgYyA4LjY0Nzg0LDguNTAxODkgMTMuODYxMywxMC45NjY2OCAyMy4yOTcxNywxMS4wMTQzMiAxMS41NDA1OCwwLjA1ODMgMjQuMTc4NDksLTYuMzg4MSAyNC4xNzg0OSwtMTIuMzMyOTkgMCwtMS4zMzk4IDAuOTU0MDQsLTIuNzIyMzYgMS44Nzg1NywtMi43MjIzNiAwLjM5MTMyLDAgMi42MTY4NiwwLjY4MzY1IDQuOTQ1NjUsMS41MTkyMyA2LjA2OTkyLDIuMTc3OSA5LjYzMDI4LDIuOTY1NDggMTQuNjA5MTIsMy4yMzE2NSA0LjkzOTk4LDAuMjY0MDkgOC41NDg0OCwtMC4xNzA0IDEzLjM1ODE3LC0xLjYwODQxIDQuNzI1NjEsLTEuNDEyODggNy40NDcwOSwtMi44NTkwNSAxNS41OTgzMywtOC4yODg4MiA0LjEwNzYsLTIuNzM2MTggNy41OTk1NCwtNC45NzQ4NyA3Ljc1OTg4LC00Ljk3NDg3IDAuMTYwMzMsMCAzLjEyNTM0LDEuNzE4OTYgNi41ODg5LDMuODE5OTEgMy40NjM1NiwyLjEwMDk1IDcuNjI1NDIsNC4zODEzMyA5LjI0ODU5LDUuMDY3NTEgMTEuMDY4NjIsNC42NzkxOCAyMy4wMjQ0NSw0LjM3MzkgMzMuOTcxMjYsLTAuODY3NDEgMS45NTc5NSwtMC45Mzc0NyA2LjU2NzkzLC0zLjczMDc0IDEwLjI0NDQsLTYuMjA3MjcgMy42NzY0OCwtMi40NzY1MyA2LjczNjEzLC00LjQ0NTc2IDYuNzk5MjMsLTQuMzc2MDYgMC4wNjMxLDAuMDY5NyAxLjQ1NjA1LDIuOTIwOCAzLjA5NTQ0LDYuMzM1NzggMS42Mzk0LDMuNDE0OTggMy42OTg5NSw3LjI2NjcgNC41NzY3OSw4LjU1OTM3IDMuODAwMDEsNS41OTU3OCA4LjE3NTg4LDkuNzUxNDEgMTQuMDgzNDMsMTMuMzc0NjQgNi4wODEyMiwzLjcyOTc1IDkuODMyMDYsOC42ODY4IDEwLjIxODgyLDEzLjUwNTA3IDAuMzgzNjcsNC43Nzk2OCAtMS43MDMyOSw5LjAxOTM5IC03LjcyMTg5LDE1LjY4NzIxIC00LjY5NzQ3LDUuMjA0MTkgLTUuODczMyw3LjIzNTQgLTUuODYxMTMsMTAuMTI0OTEgMC4wMTIyLDIuODkyNjIgMS43MDEwMyw2LjIyODU0IDQuNjY5NjQsOS4yMjM3OSA0LjgwNTMzLDQuODQ4NDQgMTIuMzQ2MDUsNi4yODc3NyAyMy40MzUzNCw0LjQ3MzE5IDIuNDc0MDgsLTAuNDA0ODQgNS41OTQ3OSwtMC43Mzc1NyA2LjkzNDkxLC0wLjczOTM4IDQuMjg1NTEsLTAuMDA2IDYuOTAzMTksMi4wOTU5NSAxMS44OTI1MSw5LjU0ODU5IDMuNDQzNTEsNS4xNDM2NSAxMC45NzM5NiwxNy43NTUwOCAxMC45NzM5NiwxOC4zNzgzNiAwLDAuMzI0MDcgLTAuMzUxNDUsMC41NTIwOCAtMC44NTA5NywwLjU1MjA4IC0xLjA1MTA5LDAgLTUuNjIzMTQsLTEuMjQzOCAtOC45MzIxNCwtMi40Mjk5NCAtNC4zNDg1LC0xLjU1ODc1IC01Ny4yNzIzOCwtMjIuMDA1MjYgLTc0Ljc0Nzg2LC0yOC44Nzc5NSAtNDYuNjYzNSwtMTguMzUxNjIgLTYyLjAyODA1LC0yNC4yMTI0NiAtNjkuNTM2NTcsLTI2LjUyNDg5IC04LjExNDE3LC0yLjQ5ODk1IC0xMy42NDAyOSwtMy4wODUyMiAtMTguMTI2NjEsLTEuOTIzMDYgLTUuNTc5OTYsMS40NDU0NiAtODEuNzIwNjcsMzAuODY4ODggLTEyNi4xMzI0NSw0OC43NDE5NSAtMjEuOTMxMTksOC44MjYgLTI0LjY3NzQ5LDkuODc1NzcgLTI4Ljc4MTE2LDExLjAwMTU5IC0zLjI2MzAzLDAuODk1MjEgLTMuMTQ0MDcsMC44ODI5NCAtMy4xNDQwNywwLjMyNDI2IHoiIC8+DQogIDwvZz4NCjwvc3ZnPg=='); background-position: 16px 80%; background-repeat: no-repeat; background-size: 20px 12px; padding-left: 2.5em; } .multi-language-selector .language-option[data-lang='kotlin'], .exampleblock[data-lang=kotlin] > .content .title { background-image: url("data:image/svg+xml;utf8,<svg viewBox='0 0 8 8' xmlns='http://www.w3.org/2000/svg'><linearGradient id='g' gradientUnits='userSpaceOnUse' x1='8' y1='0' x2='0' y2='8'><stop offset='0' stop-color='%23e44857'/><stop offset='.4689' stop-color='%23c711e1'/><stop offset='1' stop-color='%237f52ff'/></linearGradient><polygon fill='url(%23g)' points='8 8 0 8 0 0 8 0 4 4'/></svg>"); background-position: 17px 80%; background-repeat: no-repeat; background-size: 11px 11px; padding-left: 2.3em; } .multi-language-selector { display: block; } .multi-language-selector .language-option[data-lang='groovy'] { background-position: 20px center; padding-left: 32px; } .multi-language-selector .language-option[data-lang='kotlin'] { background-position: 30px center; padding-left: 27px; } .multi-language-selector .language-option { background-color: white; border: 1px solid #f7f7f8; border-radius: 4px 4px 0 0; cursor: pointer; display: inline-block; font-weight: normal; font-family: 'Lato', Arial, sans-serif; margin: 0; padding: 4px 20px; min-width: 130px; max-width: 320px; text-align: center; filter: grayscale(1); -webkit-filter: grayscale(1); opacity: 0.7; } .multi-language-selector .language-option.selected { background-color: #f7f7f8; color: #02303a; filter: none; -webkit-filter: none; opacity: 1; } .multi-language-text.hidden, .multi-language-selector ~ .multi-language-sample.hidden { display: none; } .multi-language-sample { border-radius: 0 0 4px 4px; } body.dark-theme { .multi-language-selector .language-option { background-color: #1f1f1f; border: 1px solid #1e1e22; } .multi-language-selector .language-option.selected { background-color: #2c2c2c; color: white; } } @media (prefers-color-scheme: dark) { .multi-language-selector .language-option { background-color: #1f1f1f; border: 1px solid #1e1e22; } .multi-language-selector .language-option.selected { background-color: #2c2c2c; color: white; } body.light-theme { .multi-language-selector .language-option { background-color: #white; border: 1px solid #f7f7f8; } .multi-language-selector .language-option.selected { background-color: #f7f7f8; color: #02303a; } } } </style><script type="text/javascript">function postProcessCodeBlocks() { // Assumptions: // 1) All siblings that are marked with class="multi-language-sample" should be grouped // 2) Only one language can be selected per domain (to allow selection to persist across all docs pages) // 3) There is exactly 1 small set of languages to choose from. This does not allow for multiple language preferences. For example, users cannot prefer both Kotlin and ZSH. // 4) Only 1 sample of each language can exist in the same collection. var GRADLE_DSLs = ["kotlin", "groovy"]; var preferredBuildScriptLanguage = initPreferredBuildScriptLanguage(); // Ensure preferred DSL is valid, defaulting to Kotlin DSL function initPreferredBuildScriptLanguage() { var lang = window.localStorage.getItem("preferred-gradle-dsl"); if (GRADLE_DSLs.indexOf(lang) === -1) { window.localStorage.setItem("preferred-gradle-dsl", "kotlin"); lang = "kotlin"; } return lang; } function capitalizeFirstLetter(string) { return string.charAt(0).toUpperCase() + string.slice(1); } function processSampleEl(sampleEl, prefLangId) { var codeEl = sampleEl.querySelector("code[data-lang]"); if (codeEl != null) { sampleEl.setAttribute("data-lang", codeEl.getAttribute("data-lang")); if (codeEl.getAttribute("data-lang") !== prefLangId) { sampleEl.classList.add("hidden"); } else { sampleEl.classList.remove("hidden"); } } } function switchSampleLanguage(languageId) { var multiLanguageSampleElements = [].slice.call( document.querySelectorAll(".multi-language-sample") ); // Array of Arrays, each top-level array representing a single collection of samples var multiLanguageSets = []; for (var i = 0; i < multiLanguageSampleElements.length; i++) { var currentCollection = [multiLanguageSampleElements[i]]; var currentSampleElement = multiLanguageSampleElements[i]; processSampleEl(currentSampleElement, languageId); while ( currentSampleElement.nextElementSibling != null && currentSampleElement.nextElementSibling.classList.contains( "multi-language-sample" ) ) { currentCollection.push(currentSampleElement.nextElementSibling); currentSampleElement = currentSampleElement.nextElementSibling; processSampleEl(currentSampleElement, languageId); i++; } multiLanguageSets.push(currentCollection); } multiLanguageSets.forEach(function (sampleCollection) { // Create selector element if not existing if ( sampleCollection.length > 1 && (sampleCollection[0].previousElementSibling == null || !sampleCollection[0].previousElementSibling.classList.contains( "multi-language-selector" )) ) { var languageSelectorFragment = document.createDocumentFragment(); var multiLanguageSelectorElement = document.createElement("div"); multiLanguageSelectorElement.classList.add("multi-language-selector"); languageSelectorFragment.appendChild(multiLanguageSelectorElement); sampleCollection.forEach(function (sampleEl) { var optionEl = document.createElement("code"); var sampleLanguage = sampleEl.getAttribute("data-lang"); optionEl.setAttribute("data-lang", sampleLanguage); optionEl.setAttribute("role", "button"); optionEl.classList.add("language-option"); optionEl.innerText = capitalizeFirstLetter(sampleLanguage); optionEl.addEventListener( "click", function updatePreferredLanguage(evt) { var preferredLanguageId = optionEl.getAttribute("data-lang"); window.localStorage.setItem( "preferred-gradle-dsl", preferredLanguageId ); // Record how far down the page the clicked element is before switching all samples var beforeOffset = evt.target.offsetTop; switchSampleLanguage(preferredLanguageId); // Scroll the window to account for content height differences between different sample languages window.scrollBy(0, evt.target.offsetTop - beforeOffset); } ); multiLanguageSelectorElement.appendChild(optionEl); }); sampleCollection[0].parentNode.insertBefore( languageSelectorFragment, sampleCollection[0] ); } }); [].slice .call( document.querySelectorAll(".multi-language-selector .language-option") ) .forEach(function (optionEl) { if (optionEl.getAttribute("data-lang") === languageId) { optionEl.classList.add("selected"); } else { optionEl.classList.remove("selected"); } }); [].slice .call(document.querySelectorAll(".multi-language-text")) .forEach(function (el) { if (!el.classList.contains("lang-" + languageId)) { el.classList.add("hidden"); } else { el.classList.remove("hidden"); } }); } switchSampleLanguage(preferredBuildScriptLanguage); } document.addEventListener("DOMContentLoaded", function () { postProcessCodeBlocks(); }); </script> <!-- Set siteDecorateVersion --> <script type="text/javascript"> window.siteDecorateVersion = "8.12.1"; </script> <!-- Prefetch header and footer html if on Gradle<4.4 for User Manual --> <!-- Prefetch header html for Javadoc --> <!-- Prefetch footer html if on Gradle<=8.11 for Javadoc --> <!-- Load build-tool.css if on Gradle<8.0 for Javadoc --> <!-- Load build-tool-modern.css if on Gradle>=8.0 for Javadoc --> <!-- Load build-tool.css for Release Notes --> <!-- Load decorate.css if on Gradle<=4.3 for User Manual --> <!-- Load decorate.css if on Gradle<=4.4 for DSL Reference --> <!-- Load decorate.css if on Gradle<=4.5 for Javadoc --> <!-- Load jquery.js on Gradle<=4.4 for User Manual and Javadocs, but not for Release Notes --> <!-- Load decorate.js to inject header and footer on Gradle<=4.4 for User Manual --> <!-- Load decorate.js to inject header and footer for Release Notes --> <!-- Load decorate.js to inject header and footer for Javadoc --> <!-- Load common js --> <script type="text/javascript" src="/build-tool.js"></script> <!-- Load DocSearch/Algolia assets --> <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@algolia/autocomplete-theme-classic"> <script src="https://cdn.jsdelivr.net/npm/algoliasearch@4.23.3/dist/algoliasearch-lite.umd.js"></script> <script src="https://cdn.jsdelivr.net/npm/instantsearch.js@4.69.0/dist/instantsearch.production.min.js"></script> <script src="https://cdn.jsdelivr.net/npm/@algolia/autocomplete-js"></script> <script src="/build-tool-search.js" type="text/javascript"></script> <link rel="stylesheet" href="/build-tool-search.css"> <!-- Load ratings css and js --> <link rel="stylesheet" href="/build-tool-rating.css"> <script src="/build-tool-rating.js" type="text/javascript"></script> <!-- Load Cookie Consent on User Manual --> <link rel="stylesheet" href="https://gradle.org/lib/cookie-consent-banner.css"> <style> .gradle-cookie-banner .text-footnote { color: #FFF; } </style> <script src="https://gradle.org/js/google-tag-analytics.js" id="bt-google-tag-manager-injector" consentHolderLocator="#analytics-consent-div" promo_location="gradle-documentation"> </script> <!-- Load Google Tag Manager on User Manual --> <script> (function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start': new Date().getTime(),event:'gtm.js'});var f=d.getElementsByTagName(s)[0], j=d.createElement(s),dl=l!='dataLayer'?'&l='+l:'';j.async=true;j.src= 'https://www.googletagmanager.com/gtm.js?id='+i+dl;f.parentNode.insertBefore(j,f); })(window,document,'script','dataLayer','GTM-WRTQKGT'); </script> <!-- Load canonical link and structured data for SEO --> <link rel="canonical" href="https://docs.gradle.org/current/userguide/native_software.html" /> <script type="application/ld+json"> { "@context": "http://schema.org", "@type": "WebPage", "name": "Gradle Documentation", "url": "https://docs.gradle.org/current/userguide/native_software.html" } </script> <!-- Load common Google Site Verification --> <meta name="google-site-verification" content="kCnBfMu0lbnMpfg3t1-ZgJHbSOSYRSquWsxQ4HgqLkA" /></head> <body id="native_software" class="book"><!-- Google Tag Manager (noscript) --> <noscript><iframe src="https://www.googletagmanager.com/ns.html?id=GTM-WRTQKGT" height="0" width="0" style="display:none;visibility:hidden"></iframe></noscript> <!-- End Google Tag Manager (noscript) --> <div class="layout"> <header class="site-layout__header site-header" itemscope="itemscope" itemtype="https://schema.org/WPHeader"> <nav class="site-header__navigation" itemscope="itemscope" itemtype="https://schema.org/SiteNavigationElement"> <div class="site-header__navigation-header"> <a target="_top" class="logo" href="https://docs.gradle.org" title="Gradle Docs"> <svg width="139px" height="43px" viewBox="0 0 278 86" version="1.1" xmlns="http://www.w3.org/2000/svg"> <title>Gradle</title> <path class="cls-1" d="M155,56.32V70.27a18.32,18.32,0,0,1-5.59,2.83,21.82,21.82,0,0,1-6.36.89,21.08,21.08,0,0,1-7.64-1.31A17.12,17.12,0,0,1,129.59,69a16.14,16.14,0,0,1-3.73-5.58,18.78,18.78,0,0,1-1.31-7.08,19.58,19.58,0,0,1,1.26-7.14A15.68,15.68,0,0,1,135,40a20.39,20.39,0,0,1,7.45-1.29,22,22,0,0,1,3.92.33,20.43,20.43,0,0,1,3.39.92,15.16,15.16,0,0,1,2.85,1.42A17.3,17.3,0,0,1,155,43.25l-1.84,2.91a1.72,1.72,0,0,1-1.12.84,2,2,0,0,1-1.5-.34L149,45.75a10.49,10.49,0,0,0-1.75-.79,14.33,14.33,0,0,0-2.17-.54,15.29,15.29,0,0,0-2.78-.22,11.91,11.91,0,0,0-4.61.86,9.66,9.66,0,0,0-3.52,2.46,10.9,10.9,0,0,0-2.24,3.84,14.88,14.88,0,0,0-.79,5,15.23,15.23,0,0,0,.85,5.28,11.06,11.06,0,0,0,2.38,3.94A10.15,10.15,0,0,0,138.05,68a14.28,14.28,0,0,0,8.25.44,17.1,17.1,0,0,0,2.94-1.09V61.14h-4.35a1.3,1.3,0,0,1-1-.35,1.15,1.15,0,0,1-.35-.85V56.32Zm10.47-2.93a10.53,10.53,0,0,1,2.72-3.45,5.77,5.77,0,0,1,3.72-1.25,4.5,4.5,0,0,1,2.72.74l-.38,4.41a1.18,1.18,0,0,1-.34.61,1,1,0,0,1-.61.18,6.76,6.76,0,0,1-1.06-.12,8.22,8.22,0,0,0-1.38-.12,5,5,0,0,0-1.74.28,4.37,4.37,0,0,0-1.37.83,5.55,5.55,0,0,0-1.07,1.3,12.26,12.26,0,0,0-.87,1.74V73.61H160V49.14h3.45a1.94,1.94,0,0,1,1.27.32,1.9,1.9,0,0,1,.48,1.16Zm11.36-.84A14.49,14.49,0,0,1,187,48.69a9.92,9.92,0,0,1,3.84.7,8.06,8.06,0,0,1,2.86,2,8.38,8.38,0,0,1,1.78,3,11.64,11.64,0,0,1,.61,3.82V73.61h-2.68a2.64,2.64,0,0,1-1.28-.25,1.72,1.72,0,0,1-.72-1l-.52-1.77a20.25,20.25,0,0,1-1.82,1.47,10.86,10.86,0,0,1-1.83,1.06,10.36,10.36,0,0,1-2,.66,12,12,0,0,1-2.4.22,9.64,9.64,0,0,1-2.86-.41,6.28,6.28,0,0,1-2.27-1.26,5.6,5.6,0,0,1-1.48-2.07,7.38,7.38,0,0,1-.52-2.89,5.7,5.7,0,0,1,.31-1.85,5.3,5.3,0,0,1,1-1.75,8.25,8.25,0,0,1,1.83-1.57,11.17,11.17,0,0,1,2.75-1.29,23.28,23.28,0,0,1,3.81-.9,36.77,36.77,0,0,1,5-.41V58.16a5.35,5.35,0,0,0-1.05-3.64,3.83,3.83,0,0,0-3-1.18,7.3,7.3,0,0,0-2.38.33,9.39,9.39,0,0,0-1.65.75l-1.3.75a2.52,2.52,0,0,1-1.3.34,1.7,1.7,0,0,1-1.05-.32,2.61,2.61,0,0,1-.69-.76Zm13.5,10.61a31.66,31.66,0,0,0-4.3.45,11,11,0,0,0-2.79.82,3.57,3.57,0,0,0-1.5,1.17,2.89,2.89,0,0,0,.47,3.67,3.93,3.93,0,0,0,2.39.67,7,7,0,0,0,3.14-.66,9.52,9.52,0,0,0,2.59-2Zm32.53-25V73.61h-3.6a1.39,1.39,0,0,1-1.48-1.07l-.5-2.36a12.4,12.4,0,0,1-3.4,2.74,9.17,9.17,0,0,1-4.47,1,7.95,7.95,0,0,1-6.55-3.26A11.61,11.61,0,0,1,201,66.79a19.71,19.71,0,0,1-.66-5.34,16.77,16.77,0,0,1,.74-5.06,12.21,12.21,0,0,1,2.13-4,9.88,9.88,0,0,1,3.31-2.69,9.64,9.64,0,0,1,4.34-1,8.63,8.63,0,0,1,3.51.64,9,9,0,0,1,2.6,1.74V38.17ZM217,55.39a5.94,5.94,0,0,0-2.18-1.72,6.54,6.54,0,0,0-2.54-.5,5.68,5.68,0,0,0-2.41.5A4.87,4.87,0,0,0,208,55.19a7.19,7.19,0,0,0-1.17,2.57,14.83,14.83,0,0,0-.4,3.69,16.34,16.34,0,0,0,.34,3.63,7.14,7.14,0,0,0,1,2.44,3.79,3.79,0,0,0,1.58,1.36,5,5,0,0,0,2.07.41,6,6,0,0,0,3.13-.76A9.19,9.19,0,0,0,217,66.36Zm17.67-17.22V73.61h-5.89V38.17ZM245.1,62.11a11.37,11.37,0,0,0,.67,3.26,6.54,6.54,0,0,0,1.38,2.27,5.39,5.39,0,0,0,2,1.33,7.26,7.26,0,0,0,2.61.44,8.21,8.21,0,0,0,2.47-.33,11.51,11.51,0,0,0,1.81-.74c.52-.27,1-.52,1.36-.74a2.31,2.31,0,0,1,1.13-.33,1.21,1.21,0,0,1,1.1.55L261.36,70a9.45,9.45,0,0,1-2.19,1.92,12.18,12.18,0,0,1-2.54,1.24,14,14,0,0,1-2.7.66,18.78,18.78,0,0,1-2.65.19,12.93,12.93,0,0,1-4.75-.85,10.65,10.65,0,0,1-3.82-2.5,11.8,11.8,0,0,1-2.55-4.1,15.9,15.9,0,0,1-.93-5.67,13.55,13.55,0,0,1,.81-4.71,11.34,11.34,0,0,1,2.33-3.84,11,11,0,0,1,3.69-2.59,12.31,12.31,0,0,1,4.93-1,11.86,11.86,0,0,1,4.27.74,9.25,9.25,0,0,1,3.36,2.16,9.84,9.84,0,0,1,2.21,3.48,13,13,0,0,1,.8,4.71,3.82,3.82,0,0,1-.29,1.8,1.19,1.19,0,0,1-1.1.46Zm11.23-3.55A7.28,7.28,0,0,0,256,56.4a5.16,5.16,0,0,0-1-1.77,4.44,4.44,0,0,0-1.63-1.21,5.68,5.68,0,0,0-2.3-.44,5.46,5.46,0,0,0-4,1.45,7.13,7.13,0,0,0-1.87,4.13ZM112.26,14a13.72,13.72,0,0,0-19.08-.32,1.27,1.27,0,0,0-.41.93,1.31,1.31,0,0,0,.38.95l1.73,1.73a1.31,1.31,0,0,0,1.71.12,7.78,7.78,0,0,1,4.71-1.57,7.87,7.87,0,0,1,5.57,13.43C96,40.2,81.41,9.66,48.4,25.37a4.48,4.48,0,0,0-2,6.29l5.66,9.79a4.49,4.49,0,0,0,6.07,1.67l.14-.08-.11.08,2.51-1.41a57.72,57.72,0,0,0,7.91-5.89,1.37,1.37,0,0,1,1.8-.06h0a1.29,1.29,0,0,1,0,2A59.79,59.79,0,0,1,62.11,44l-.09.05-2.51,1.4a7,7,0,0,1-3.47.91,7.19,7.19,0,0,1-6.23-3.57l-5.36-9.24C34.17,40.81,27.93,54.8,31.28,72.5a1.31,1.31,0,0,0,1.29,1.06h6.09A1.3,1.3,0,0,0,40,72.42a8.94,8.94,0,0,1,17.73,0A1.3,1.3,0,0,0,59,73.56h5.94a1.31,1.31,0,0,0,1.3-1.14,8.93,8.93,0,0,1,17.72,0,1.3,1.3,0,0,0,1.29,1.14h5.87a1.3,1.3,0,0,0,1.3-1.28c.14-8.28,2.37-17.79,8.74-22.55C123.15,33.25,117.36,19.12,112.26,14ZM89.79,38.92l-4.2-2.11h0a2.64,2.64,0,1,1,4.2,2.12Z"/> </svg> </a> <div class="site-header__doc-type sr-only">User Manual</div> <div class="site-header-version"></div> <button type="button" aria-label="Navigation Menu" class="site-header__navigation-button hamburger"> <span class="hamburger__bar"></span> <span class="hamburger__bar"></span> <span class="hamburger__bar"></span> </button> </div> <div class="site-header__navigation-collapsible site-header__navigation-collapsible--collapse"> <ul class="site-header__navigation-items"> <li id="theme-toggle" class="site-header__navigation-item"> <a class="site-header__navigation-link theme-toggle" title="Theme"> <svg width="24" height="24" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"> <title>Theme</title> <path d="m12 22c5.5228475 0 10-4.4771525 10-10s-4.4771525-10-10-10-10 4.4771525-10 10 4.4771525 10 10 10zm0-1.5v-17c4.6944204 0 8.5 3.80557963 8.5 8.5 0 4.6944204-3.8055796 8.5-8.5 8.5z"/> </svg> </a> <script type="text/javascript"> const btn = document.querySelector(".theme-toggle"); const prefersDarkScheme = window.matchMedia("(prefers-color-scheme: dark)"); const currentTheme = localStorage.getItem("theme"); if (currentTheme == "dark") { document.body.classList.toggle("dark-theme"); } else if (currentTheme == "light") { document.body.classList.toggle("light-theme"); } btn.addEventListener("click", function () { if (prefersDarkScheme.matches) { document.body.classList.toggle("light-theme"); var theme = document.body.classList.contains("light-theme")? "light" : "dark"; } else { document.body.classList.toggle("dark-theme"); var theme = document.body.classList.contains("dark-theme")? "dark" : "light"; } localStorage.setItem("theme", theme); }); </script> </li> <li class="site-header__navigation-item site-header__navigation-submenu-section" tabindex="0"> <span class="site-header__navigation-link"> Community </span> <div class="site-header__navigation-submenu"> <div class="site-header__navigation-submenu-item" itemprop="name"> <a target="_top" class="site-header__navigation-submenu-item-link" href="https://gradle.org/" itemprop="url"> <span class="site-header__navigation-submenu-item-link-text">Community Home</span> </a> </div> <div class="site-header__navigation-submenu-item" itemprop="name"> <a target="_top" class="site-header__navigation-submenu-item-link" href="https://discuss.gradle.org/" itemprop="url"> <span class="site-header__navigation-submenu-item-link-text">Community Forums</span> </a> </div> <div class="site-header__navigation-submenu-item" itemprop="name"> <a target="_top" class="site-header__navigation-submenu-item-link" href="https://plugins.gradle.org" itemprop="url"> <span class="site-header__navigation-submenu-item-link-text">Community Plugins</span> </a> </div> </div> </li> <li class="site-header__navigation-item" itemprop="name"> <a target="_top" class="site-header__navigation-link" href="https://dpeuniversity.gradle.com/" itemprop="url">DPE University</a> </li> <li class="site-header__navigation-item" itemprop="name"> <a target="_top" class="site-header__navigation-link" href="https://gradle.org/training/" itemprop="url">Events</a> </li> <li class="site-header__navigation-item site-header__navigation-submenu-section" tabindex="0"> <span class="site-header__navigation-link"> News </span> <div class="site-header__navigation-submenu"> <div class="site-header__navigation-submenu-item" itemprop="name"> <a class="site-header__navigation-submenu-item-link" href="https://newsletter.gradle.org" itemprop="url"> <span class="site-header__navigation-submenu-item-link-text">Newsletter</span> </a> </div> <div class="site-header__navigation-submenu-item" itemprop="name"> <a class="site-header__navigation-submenu-item-link" href="https://blog.gradle.org" itemprop="url"> <span class="site-header__navigation-submenu-item-link-text">Blog</span> </a> </div> <div class="site-header__navigation-submenu-item"> <a class="site-header__navigation-submenu-item-link" href="https://twitter.com/gradle"> <span class="site-header__navigation-submenu-item-link-text">Twitter</span> </a> </div> </div> </li> <li class="site-header__navigation-item" itemprop="name"> <a target="_top" class="site-header__navigation-link" href="https://gradle.com/develocity" itemprop="url">Develocity</a> </li> <li class="site-header__navigation-item"> <a class="site-header__navigation-link" title="Gradle on GitHub" href="https://github.com/gradle/gradle"> <svg width="20" height="20" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"> <title>Github</title> <path d="M10 0C4.477 0 0 4.477 0 10c0 4.418 2.865 8.166 6.839 9.489.5.092.682-.217.682-.482 0-.237-.008-.866-.013-1.7-2.782.603-3.369-1.342-3.369-1.342-.454-1.155-1.11-1.462-1.11-1.462-.908-.62.069-.608.069-.608 1.003.07 1.531 1.03 1.531 1.03.892 1.529 2.341 1.087 2.91.831.092-.646.35-1.086.636-1.336-2.22-.253-4.555-1.11-4.555-4.943 0-1.091.39-1.984 1.029-2.683-.103-.253-.446-1.27.098-2.647 0 0 .84-.268 2.75 1.026A9.578 9.578 0 0 1 10 4.836c.85.004 1.705.114 2.504.337 1.909-1.294 2.747-1.026 2.747-1.026.546 1.377.203 2.394.1 2.647.64.699 1.028 1.592 1.028 2.683 0 3.842-2.339 4.687-4.566 4.935.359.309.678.919.678 1.852 0 1.336-.012 2.415-.012 2.743 0 .267.18.579.688.481C17.137 18.163 20 14.418 20 10c0-5.523-4.478-10-10-10" fill-rule="evenodd";/> </svg> </a> </li> </ul> </div> </nav> </header> <main class="main-content"> <!-- Primary Navigation --> <nav class="docs-navigation"> <div class="search-container"></div> <h3 id="overview">Overview</h3> <ul> <li><a href="../userguide/userguide.html">What is Gradle?</a></li> <li><a href="../userguide/quick_start.html">Quick Start</a></li> </ul> <h3 id="what-is-new">Releases</h3> <ul> <li><a href="https://gradle.org/releases/">All Releases</a></li> <li><a href="../release-notes.html">Release Notes</a></li> <li><a href="../userguide/installation.html">Installing Gradle</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#upgrading-gradle" aria-expanded="false" aria-controls="upgrading-gradle">Upgrading Gradle</a> <ul id="upgrading-gradle"> <li><a href="../userguide/upgrading_version_8.html">version 8.X to latest</a></li> <li><a href="../userguide/upgrading_version_7.html">version 7.X to 8.0</a></li> <li><a href="../userguide/upgrading_version_6.html">version 6.X to 7.0</a></li> <li><a href="../userguide/upgrading_version_5.html">version 5.X to 6.0</a></li> <li><a href="../userguide/upgrading_version_4.html">version 4.X to 5.0</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#migrating-to-gradle" aria-expanded="false" aria-controls="migrating-to-gradle">Migrating to Gradle</a> <ul id="migrating-to-gradle"> <li><a href="../userguide/migrating_from_maven.html">from Maven</a></li> <li><a href="../userguide/migrating_from_ant.html">from Ant</a></li> </ul> </li> <li><a href="../userguide/troubleshooting.html">Troubleshooting</a></li> <li><a href="../userguide/compatibility.html">Compatibility Notes</a></li> <li><a href="../userguide/feature_lifecycle.html">Gradle's Feature Lifecycle</a></li> </ul> <h3 id="running-gradle-builds">Running Gradle Builds</h3> <ul> <li><a href="../userguide/getting_started_eng.html">Getting Started</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#running-introduction" aria-expanded="false" aria-controls="introduction">Learning the Basics</a> <ul id="running-introduction"> <li><a href="../userguide/gradle_basics.html">1. Gradle Basics</a></li> <li><a href="../userguide/gradle_wrapper_basics.html">2. Gradle Wrapper Basics</a></li> <li><a href="../userguide/command_line_interface_basics.html">3. Command-Line Interface Basics</a></li> <li><a href="../userguide/settings_file_basics.html">4. Settings File Basics</a></li> <li><a href="../userguide/build_file_basics.html">5. Build File Basics</a></li> <li><a href="../userguide/dependency_management_basics.html">6. Dependency Management Basics</a></li> <li><a href="../userguide/task_basics.html">7. Task Basics</a></li> <li><a href="../userguide/plugin_basics.html">8. Plugins Basics</a></li> <li><a href="../userguide/gradle_optimizations.html">9. Incremental Builds + Caching</a></li> <li><a href="../userguide/build_scans.html">10. Build Scans</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" aria-expanded="false">Beginner Tutorial</a> <ul id="running-tutorial"> <li><a href="../userguide/part1_gradle_init.html">1. Initializing the Project</a></li> <li><a href="../userguide/part2_gradle_tasks.html">2. Running Tasks</a></li> <li><a href="../userguide/part3_gradle_dep_man.html">3. Understanding Dependencies</a></li> <li><a href="../userguide/part4_gradle_plugins.html">4. Applying Plugins</a></li> <li><a href="../userguide/part5_gradle_inc_builds.html">5. Exploring Incremental Builds</a></li> <li><a href="../userguide/part6_gradle_caching.html">6. Enabling the Build Cache</a></li> <li><a href="../userguide/part7_gradle_refs.html">7. Using Reference Materials</a></li> </ul> </li> <li><a href="../userguide/gradle_ides.html">Gradle in the IDE</a></li> </ul> <h3 id="authoring-gradle-builds">Authoring Gradle Builds</h3> <ul> <li><a href="../userguide/getting_started_dev.html">Getting Started</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#learning-the-basics" aria-expanded="false" aria-controls="learning-the-basics">Learning the Basics</a> <ul id="authoring-introduction"> <li><a href="../userguide/gradle_directories.html">1. Gradle Directories</a></li> <li><a href="../userguide/intro_multi_project_builds.html">2. Multi-Project Builds</a></li> <li><a href="../userguide/build_lifecycle.html">3. Gradle Build Lifecycle</a></li> <li><a href="../userguide/writing_settings_files.html">4. Writing Settings Files</a></li> <li><a href="../userguide/writing_build_scripts.html">5. Writing Build Scripts</a></li> <li><a href="../userguide/tutorial_using_tasks.html">6. Using Tasks</a></li> <li><a href="../userguide/writing_tasks.html">7. Writing Tasks</a></li> <li><a href="../userguide/plugins.html">8. Using Plugins</a></li> <li><a href="../userguide/writing_plugins.html">9. Writing Plugins</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" aria-expanded="false">Advanced Tutorial</a> <ul id="authoring-tutorial"> <li><a href="../userguide/part1_gradle_init_project.html">1. Initializing the Project</a></li> <li><a href="../userguide/part2_build_lifecycle.html">2. Understanding the Build Lifecycle</a></li> <li><a href="../userguide/part3_multi_project_builds.html">3. Multi-Project Builds</a></li> <li><a href="../userguide/part4_settings_file.html">4. Writing the Settings File</a></li> <li><a href="../userguide/part5_build_scripts.html">5. Writing a Build Script</a></li> <li><a href="../userguide/part6_writing_tasks.html">6. Writing Tasks</a></li> <li><a href="../userguide/part7_writing_plugins.html">7. Writing Plugins</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#gradle-properties" aria-expanded="false" aria-controls="gradle-properties">Gradle Types</a> <ul id="gradle-properties-topics"> <li><a href="../userguide/properties_providers.html">Understanding Properties and Providers</a></li> <li><a href="../userguide/collections.html">Understanding Collections</a></li> <li><a href="../userguide/service_injection.html">Understanding Services and Service Injection</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#authoring-multi-project-builds" aria-expanded="false" aria-controls="authoring-multi-project-builds">Structuring Builds</a> <ul id="authoring-multi-project-builds"> <li><a href="../userguide/multi_project_builds.html">Structuring Projects with Gradle</a></li> <li><a href="../userguide/declaring_dependencies_between_subprojects.html">Declaring Dependencies between Subprojects</a></li> <li><a href="../userguide/sharing_build_logic_between_subprojects.html">Sharing Build Logic between Subprojects</a></li> <li><a href="../userguide/composite_builds.html">Composite Builds</a></li> <li><a href="../userguide/multi_project_configuration_and_execution.html">Configuration on Demand</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#developing-tasks" aria-expanded="false" aria-controls="developing-tasks">Developing Tasks</a> <ul id="developing-tasks"> <li><a href="../userguide/more_about_tasks.html">Understanding Tasks</a></li> <li><a href="../userguide/controlling_task_execution.html">Controlling Task Execution</a></li> <li><a href="../userguide/organizing_tasks.html">Organizing Tasks</a></li> <li><a href="../userguide/implementing_custom_tasks.html">Implementing Custom Tasks</a></li> <li><a href="../userguide/lazy_configuration.html">Configuring Tasks Lazily</a></li> <li><a href="../userguide/worker_api.html">Developing Parallel Tasks</a></li> <li><a href="../userguide/custom_tasks.html">Developing Advanced Tasks</a></li> <li><a href="../userguide/build_services.html">Using Shared Build Services</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#developing-plugins" aria-expanded="false" aria-controls="developing-plugins">Developing Plugins</a> <ul id="developing-plugins"> <li><a href="../userguide/custom_plugins.html">Understanding Plugins</a></li> <li><a href="../userguide/implementing_gradle_plugins.html">Understanding Implementation Options</a></li> <li><a href="../userguide/implementing_gradle_plugins_precompiled.html">Implementing Pre-compiled Script Plugins</a></li> <li><a href="../userguide/implementing_gradle_plugins_binary.html">Implementing Binary Plugins</a></li> <li><a href="../userguide/testing_gradle_plugins.html">Testing Plugins</a></li> <li><a href="../userguide/publishing_gradle_plugins.html">Publishing Plugins</a></li> <li><a href="../userguide/reporting_problems.html">Reporting Problems</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#other-developing-topics" aria-expanded="false" aria-controls="other-developing-topics">Other Topics</a> <ul id="other-developing-topics"> <li><a href="../userguide/working_with_files.html">Working with Files</a></li> <li><a href="../userguide/init_scripts.html">Initialization Scripts</a></li> <li><a href="../userguide/dataflow_actions.html">Dataflow Actions</a></li> <li><a href="../userguide/test_kit.html">Testing with TestKit</a></li> <li><a href="../userguide/ant.html">Using Ant from Gradle</a></li> </ul> </li> </ul> <h3 id="optimizing-build-performance">Optimizing Gradle Builds</h3> <ul> <li><a href="../userguide/build_environment.html">Configuring the Build Environment</a></li> <li><a href="../userguide/directory_layout.html">Gradle-managed Directories</a></li> <li><a href="../userguide/logging.html">Logging with Gradle</a></li> <li><a href="../userguide/config_gradle.html">Configuring Gradle</a></li> <li><a href="../userguide/performance.html">Improving Performance</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#build-cache" aria-expanded="false" aria-controls="optimizing-build-performance">Build Cache</a> <ul id="build-cache"> <li><a href="../userguide/build_cache.html">Enabling and Configuring</a></li> <li><a href="../userguide/build_cache_use_cases.html">Why use the Build Cache?</a></li> <li><a href="../userguide/build_cache_performance.html">Understanding the Impact</a></li> <li><a href="../userguide/build_cache_concepts.html">Learning Basic Concepts</a></li> <li><a href="../userguide/caching_java_projects.html">Caching Java Project</a></li> <li><a href="../userguide/caching_android_projects.html">Caching Android Project</a></li> <li><a href="../userguide/build_cache_debugging.html">Debugging Caching Issues</a></li> <li><a href="../userguide/common_caching_problems.html">Troubleshooting</a></li> </ul> </li> <li><a href="../userguide/configuration_cache.html">Configuration Cache</a></li> <li><a href="../userguide/continuous_builds.html">Continuous Builds</a></li> <li><a href="../userguide/inspect.html">Inspecting Builds</a></li> <li><a href="../userguide/isolated_projects.html">Isolated Projects</a></li> <li><a href="../userguide/file_system_watching.html">File System Watching</a></li> </ul> <h3 id="managing-dependencies">Dependency Management</h3> <ul> <li><a href="../userguide/getting_started_dep_man.html">Getting Started</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#learning-the-basics-dependency-management" aria-expanded="false" aria-controls="learning-the-basics-dependency-management">Learning the Basics</a> <ul id="learning-the-basics-dependency-management"> <li><a href="../userguide/declaring_dependencies.html">1. Declaring Dependencies</a></li> <li><a href="../userguide/dependency_configurations.html">2. Dependency Configurations</a></li> <li><a href="../userguide/declaring_repositories.html">3. Declaring Repositories</a></li> <li><a href="../userguide/centralizing_dependencies.html">4. Centralizing Dependencies</a></li> <li><a href="../userguide/dependency_constraints_conflicts.html">5. Dependency Constraints and Conflict Resolution</a></li> <li><a href="../userguide/dependency_resolution.html">6. Dependency Resolution</a></li> <li><a href="../userguide/variant_aware_resolution.html">7. Variant Aware Dependency Resolution</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#declaring-dependencies" aria-expanded="false" aria-controls="declaring-dependencies">Declaring Dependencies</a> <ul id="declaring-dependencies"> <li><a href="../userguide/declaring_dependencies_basics.html">Declaring Dependencies Basics</a></li> <li><a href="../userguide/viewing_debugging_dependencies.html">Viewing Dependencies</a></li> <li><a href="../userguide/dependency_versions.html">Declaring Versions and Ranges</a></li> <li><a href="../userguide/dependency_constraints.html">Declaring Dependency Constraints</a></li> <li><a href="../userguide/declaring_configurations.html">Creating Dependency Configurations</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#declaring-repositories" aria-expanded="false" aria-controls="declaring-repositories">Declaring Repositories</a> <ul id="declaring-repositories"> <li><a href="../userguide/declaring_repositories_basics.html">Declaring Repositories Basics</a></li> <li><a href="../userguide/centralizing_repositories.html">Centralizing Repository Declarations</a></li> <li><a href="../userguide/supported_repository_types.html">Repository Types</a></li> <li><a href="../userguide/supported_metadata_formats.html">Metadata Formats</a></li> <li><a href="../userguide/supported_repository_protocols.html">Supported Protocols</a></li> <li><a href="../userguide/filtering_repository_content.html">Filtering Repository Content</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#centralizing-dependencies" aria-expanded="false" aria-controls="centralizing-dependencies">Centralizing Dependencies</a> <ul id="centralizing-dependencies"> <li><a href="../userguide/platforms.html">Creating Platforms</a></li> <li><a href="../userguide/version_catalogs.html">Creating Version Catalogs</a></li> <li><a href="../userguide/centralizing_catalog_platform.html">Using Catalogs with Platforms</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#dependency-management" aria-expanded="false" aria-controls="dependency-management">Managing Dependencies</a> <ul id="dependency-management"> <li><a href="../userguide/dependency_locking.html">Locking Versions</a></li> <li><a href="../userguide/resolution_rules.html">Using Resolution Rules</a></li> <li><a href="../userguide/component_metadata_rules.html">Modifying Dependency Metadata</a></li> <li><a href="../userguide/dependency_caching.html">Caching Dependencies</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#understanding_dep_res" aria-expanded="false" aria-controls="understanding_dep_res">Understanding Dependency Resolution</a> <ul id="understanding_dep_res"> <li><a href="../userguide/variant_model.html">Understanding The Model</a></li> <li><a href="../userguide/component_capabilities.html">Capabilities</a></li> <li><a href="../userguide/variant_attributes.html">Variants and Attributes</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#dependency-resolution" aria-expanded="false" aria-controls="dependency-resolution">Controlling Dependency Resolution</a> <ul id="dependency-resolution"> <li><a href="../userguide/dependency_resolution_basics.html">Dependency Resolution Basics</a></li> <li><a href="../userguide/dependency_graph_resolution.html">Graph Resolution</a></li> <li><a href="../userguide/artifact_resolution.html">Artifact Resolution</a></li> <li><a href="../userguide/artifact_transforms.html">Artifact Transforms</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#publishing" aria-expanded="false" aria-controls="publishing">Publishing Libraries</a> <ul id="publishing"> <li><a href="../userguide/publishing_setup.html">Setting up Publishing</a></li> <li><a href="../userguide/publishing_gradle_module_metadata.html">Understanding Gradle Module Metadata</a></li> <li><a href="../userguide/publishing_signing.html">Signing Artifacts</a></li> <li><a href="../userguide/publishing_customization.html">Customizing Publishing</a></li> <li><a href="../userguide/publishing_maven.html">Maven Publish Plugin</a></li> <li><a href="../userguide/publishing_ivy.html">Ivy Publish Plugin</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#other" aria-expanded="false" aria-controls="other">Other Topics</a> <ul id="other"> <li><a href="../userguide/dependency_verification.html">Verifying Dependencies</a></li> <li><a href="../userguide/dependency_version_alignment.html">Aligning Dependencies</a></li> <li><a href="../userguide/feature_variants.html">Modeling Feature Variants and Optional Dependencies</a></li> </ul> </li> </ul> <h3 id="platforms">Platforms</h3> <ul> <li><a class="nav-dropdown" data-toggle="collapse" href="#jvm" aria-expanded="false" aria-controls="jvm">JVM Builds</a> <ul id="jvm"> <li><a href="../userguide/building_java_projects.html">Building Java &amp; JVM projects</a></li> <li><a href="../userguide/java_testing.html">Testing Java &amp; JVM projects</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#java-toolchains" aria-expanded="false" aria-controls="java-toolchains">Java Toolchains</a> <ul id="java-toolchains"> <li><a href="../userguide/toolchains.html">Toolchains for JVM projects</a></li> <li><a href="../userguide/toolchain_plugins.html">Toolchain Resolver Plugins</a></li> </ul> </li> <li><a href="../userguide/dependency_management_for_java_projects.html">Managing Dependencies</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#jvm-plugins" aria-expanded="false" aria-controls="jvm-plugins">JVM Plugins</a> <ul id="jvm-plugins"> <li><a href="../userguide/java_library_plugin.html">Java Library Plugin</a></li> <li><a href="../userguide/application_plugin.html">Java Application Plugin</a></li> <li><a href="../userguide/java_platform_plugin.html">Java Platform Plugin</a></li> <li><a href="../userguide/groovy_plugin.html">Groovy Plugin</a></li> <li><a href="../userguide/scala_plugin.html">Scala Plugin</a></li> </ul> </li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#cpp" aria-expanded="false" aria-controls="cpp">C++ Builds</a> <ul id="cpp"> <li><a href="../userguide/building_cpp_projects.html">Building C++ projects</a></li> <li><a href="../userguide/cpp_testing.html">Testing C++ projects</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#swift" aria-expanded="false" aria-controls="swift">Swift Builds</a> <ul id="swift"> <li><a href="../userguide/building_swift_projects.html">Building Swift projects</a></li> <li><a href="../userguide/swift_testing.html">Testing Swift projects</a></li> </ul> </li> </ul> <h3 id="third-party-integration">Integration</h3> <ul> <li><a href="../userguide/third_party_integration.html">Third-party Tools</a></li> </ul> <h3 id="reference">Reference</h3> <ul> <li><a class="nav-dropdown" data-toggle="collapse" href="#gradle-api" aria-expanded="false" aria-controls="gradle-api">Gradle DSLs and API</a> <ul id="gradle-api"> <li><a href="../javadoc/index.html?overview-summary.html">Javadoc</a></li> <li><a href="../userguide/groovy_build_script_primer.html">Groovy DSL Primer</a></li> <li><a href="../dsl/index.html">Groovy DSL Reference</a></li> <li><a href="../userguide/kotlin_dsl.html">Kotlin DSL Primer</a></li> <li><a href="../kotlin-dsl/index.html" target="_blank">Kotlin DSL API</a></li> <li><a href="../userguide/migrating_from_groovy_to_kotlin_dsl.html">Groovy to Kotlin DSL Migration</a></li> </ul> </li> <li><a href="../userguide/gradle_wrapper.html">Gradle Wrapper</a></li> <li><a href="../userguide/gradle_daemon.html">Gradle Daemon</a></li> <li><a href="../userguide/command_line_interface.html">Command-Line Interface</a></li> <li><a class="nav-dropdown" data-toggle="collapse" href="#core-plugins" aria-expanded="false" aria-controls="core-plugins">Core Plugins</a> <ul id="core-plugins"> <li><a href="../userguide/plugin_reference.html">List of Core Plugins</a></li> </ul> </li> <li><a class="nav-dropdown" data-toggle="collapse" href="#howto" aria-expanded="false" aria-controls="other">How To Guides</a> <ul id="howto"> <li><a href="../userguide/cross_project_publications.html">How to share outputs between projects</a></li> </ul> </li> <li><a href="../samples/index.html">Samples</a></li> <li><a href="../userguide/glossary.html">Glossary</a></li> <li><a href="https://community.gradle.org/cookbook/">Cookbook</a></li> <li><a href="../userguide/userguide_single.html">Single Page Version</a></li> <li><a href="../userguide/userguide.pdf">PDF Version</a></li> </ul> </nav> <!-- End Primary Navigation --> <div class="content"> <div class="chapter"> <div id="header"> <h1>Building native software</h1> <div class="details"> <span id="revnumber">version 8.12.1</span> </div> <div id="toc" class="toc"> <div id="toctitle">Contents</div> <ul class="sectlevel1"> <li><a href="#sec:native_features">Features</a></li> <li><a href="#sec:supported_languages">Supported languages</a></li> <li><a href="#native-binaries:tool-chain-support">Tool chain support</a></li> <li><a href="#sec:tool_chain_installation">Tool chain installation</a></li> <li><a href="#sec:native_software_model">Native software model</a></li> <li><a href="#sec:parallel_compilation">Parallel Compilation</a></li> <li><a href="#sec:building_a_library">Building a library</a></li> <li><a href="#sec:building_an_executable">Building an executable</a></li> <li><a href="#sec:dependents">Assembling or building dependents</a></li> <li><a href="#sec:native_tasks">Tasks</a></li> <li><a href="#sec:finding_out_more_about_your_project">Finding out more about your project</a></li> <li><a href="#native_binaries:languages">Language support</a></li> <li><a href="#sec:configuring_the_compiler_assembler_and_linker">Configuring the compiler, assembler and linker</a></li> <li><a href="#native_binaries:windows-resources">Windows Resources</a></li> <li><a href="#sec:library_dependencies">Library Dependencies</a></li> <li><a href="#native_binaries:preCompiledHeaders">Precompiled Headers</a></li> <li><a href="#native_binaries:variants">Native Binary Variants</a></li> <li><a href="#native_binaries:tool_chain">Tool chains</a></li> <li><a href="#native_binaries:visual_studio">Visual Studio IDE integration</a></li> <li><a href="#native_binaries:cunit">CUnit support</a></li> <li><a href="#native_binaries:google_test">GoogleTest support</a></li> </ul> </div> </div> <div id="content"> <div id="preamble"> <div class="sectionbody"> <div class="admonitionblock caution"> <table> <tr> <td class="icon"> <i class="fa icon-caution" title="Caution"></i> </td> <td class="content"> The <a href="https://blog.gradle.org/state-and-future-of-the-gradle-software-model">software model</a> is being retired and the plugins mentioned in this chapter will eventually be deprecated and removed. We recommend new projects looking to build C++ applications and libraries use the newer <a href="building_cpp_projects.html#building_cpp_projects">replacement plugins</a>. </td> </tr> </table> </div> <div class="paragraph"> <p>The native software plugins add support for building native software components, such as executables or shared libraries, from code written in C++, C and other languages. While many excellent build tools exist for this space of software development, Gradle offers developers its trademark power and flexibility together with dependency management practices more traditionally found in the JVM development space.</p> </div> <div class="paragraph"> <p>The native software plugins make use of the Gradle software model.</p> </div> </div> </div> <div class="sect1"> <h2 id="sec:native_features"><a class="anchor" href="#sec:native_features"></a><a class="link" href="#sec:native_features">Features</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>The native software plugins provide:</p> </div> <div class="ulist"> <ul> <li> <p>Support for building native libraries and applications on Windows, Linux, macOS and other platforms.</p> </li> <li> <p>Support for several source languages.</p> </li> <li> <p>Support for building different variants of the same software, for different architectures, operating systems, or for any purpose.</p> </li> <li> <p>Incremental parallel compilation, precompiled headers.</p> </li> <li> <p>Dependency management between native software components.</p> </li> <li> <p>Unit test execution.</p> </li> <li> <p>Generate Visual studio solution and project files.</p> </li> <li> <p>Deep integration with various tool chain, including discovery of installed tool chains.</p> </li> </ul> </div> </div> </div> <div class="sect1"> <h2 id="sec:supported_languages"><a class="anchor" href="#sec:supported_languages"></a><a class="link" href="#sec:supported_languages">Supported languages</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>The following source languages are currently supported:</p> </div> <div class="ulist"> <ul> <li> <p>C</p> </li> <li> <p>C++</p> </li> <li> <p>Objective-C</p> </li> <li> <p>Objective-C++</p> </li> <li> <p>Assembly</p> </li> <li> <p>Windows resources</p> </li> </ul> </div> </div> </div> <div class="sect1"> <h2 id="native-binaries:tool-chain-support"><a class="anchor" href="#native-binaries:tool-chain-support"></a><a class="link" href="#native-binaries:tool-chain-support">Tool chain support</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Gradle offers the ability to execute the same build using different tool chains. When you build a native binary, Gradle will attempt to locate a tool chain installed on your machine that can build the binary. You can fine tune exactly how this works, see <a href="#native_binaries:tool_chain">Tool chain support</a> for details.</p> </div> <div class="paragraph"> <p>The following tool chains are supported:</p> </div> <table class="tableblock frame-all grid-all fit-content"> <colgroup> <col> <col> <col> </colgroup> <thead> <tr> <th class="tableblock halign-left valign-top">Operating System</th> <th class="tableblock halign-left valign-top">Tool Chain</th> <th class="tableblock halign-left valign-top">Notes</th> </tr> </thead> <tbody> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Linux</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://gcc.gnu.org/">GCC</a></p></td> <td class="tableblock halign-left valign-top"></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Linux</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://clang.llvm.org">Clang</a></p></td> <td class="tableblock halign-left valign-top"></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">macOS</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">XCode</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Uses the Clang tool chain bundled with XCode.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="https://visualstudio.microsoft.com/">Visual C++</a></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows XP and later, Visual C++ 2010/2012/2013/2015/2017/2019.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://gcc.gnu.org/">GCC</a> with <a href="http://cygwin.com">Cygwin 32 and Cygwin 64</a></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows XP and later.</p></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://gcc.gnu.org/">GCC</a> with <a href="http://www.mingw.org/">MinGW</a> and <a href="https://mingw-w64.org/doku.php">MinGW64</a></p></td> <td class="tableblock halign-left valign-top"><p class="tableblock">Windows XP and later.</p></td> </tr> </tbody> </table> <div class="paragraph"> <p>The following tool chains are unofficially supported. They generally work fine, but are not tested continuously:</p> </div> <table class="tableblock frame-all grid-all fit-content"> <colgroup> <col> <col> <col> </colgroup> <thead> <tr> <th class="tableblock halign-left valign-top">Operating System</th> <th class="tableblock halign-left valign-top">Tool Chain</th> <th class="tableblock halign-left valign-top">Notes</th> </tr> </thead> <tbody> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">macOS</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://gcc.gnu.org/">GCC</a> from Macports</p></td> <td class="tableblock halign-left valign-top"></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">macOS</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://clang.llvm.org">Clang</a> from Macports</p></td> <td class="tableblock halign-left valign-top"></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">UNIX-like</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://gcc.gnu.org/">GCC</a></p></td> <td class="tableblock halign-left valign-top"></td> </tr> <tr> <td class="tableblock halign-left valign-top"><p class="tableblock">UNIX-like</p></td> <td class="tableblock halign-left valign-top"><p class="tableblock"><a href="http://clang.llvm.org">Clang</a></p></td> <td class="tableblock halign-left valign-top"></td> </tr> </tbody> </table> </div> </div> <div class="sect1"> <h2 id="sec:tool_chain_installation"><a class="anchor" href="#sec:tool_chain_installation"></a><a class="link" href="#sec:tool_chain_installation">Tool chain installation</a></h2> <div class="sectionbody"> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> Note that if you are using GCC then you currently need to install support for C++, even if you are not building from C++ source. This restriction will be removed in a future Gradle version. </td> </tr> </table> </div> <div class="paragraph"> <p>To build native software, you will need to have a compatible tool chain installed:</p> </div> <div class="sect2"> <h3 id="sec:windows"><a class="anchor" href="#sec:windows"></a><a class="link" href="#sec:windows">Windows</a></h3> <div class="paragraph"> <p>To build on Windows, install a compatible version of Visual Studio. The native plugins will discover the Visual Studio installations and select the latest version. There is no need to mess around with environment variables or batch scripts. This works fine from a Cygwin shell or the Windows command-line.</p> </div> <div class="paragraph"> <p>Alternatively, you can install Cygwin with GCC or MinGW. Clang is currently not supported.</p> </div> </div> <div class="sect2"> <h3 id="sec:macOS"><a class="anchor" href="#sec:macOS"></a><a class="link" href="#sec:macOS">macOS</a></h3> <div class="paragraph"> <p>To build on macOS, you should install XCode. The native plugins will discover the XCode installation using the system PATH.</p> </div> <div class="paragraph"> <p>The native plugins also work with GCC and Clang bundled with Macports. To use one of the Macports tool chains, you will need to make the tool chain the default using the <code>port select</code> command and add Macports to the system PATH.</p> </div> </div> <div class="sect2"> <h3 id="sec:linux"><a class="anchor" href="#sec:linux"></a><a class="link" href="#sec:linux">Linux</a></h3> <div class="paragraph"> <p>To build on Linux, install a compatible version of GCC or Clang. The native plugins will discover GCC or Clang using the system PATH.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:native_software_model"><a class="anchor" href="#sec:native_software_model"></a><a class="link" href="#sec:native_software_model">Native software model</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>The native software model builds on the base Gradle software model.</p> </div> <div class="paragraph"> <p>To build native software using Gradle, your project should define one or more <em>native components</em>. Each component represents either an executable or a library that Gradle should build. A project can define any number of components. Gradle does not define any components by default.</p> </div> <div class="paragraph"> <p>For each component, Gradle defines a <em>source set</em> for each language that the component can be built from. A source set is essentially just a set of source directories containing source files. For example, when you apply the <code>c</code> plugin and define a library called <code>helloworld</code>, Gradle will define, by default, a source set containing the C source files in the <code>src/helloworld/c</code> directory. It will use these source files to build the <code>helloworld</code> library. This is described in more detail below.</p> </div> <div class="paragraph"> <p>For each component, Gradle defines one or more <em>binaries</em> as output. To build a binary, Gradle will take the source files defined for the component, compile them as appropriate for the source language, and link the result into a binary file. For an executable component, Gradle can produce executable binary files. For a library component, Gradle can produce both static and shared library binary files. For example, when you define a library called <code>helloworld</code> and build on Linux, Gradle will, by default, produce <code>libhelloworld.so</code> and <code>libhelloworld.a</code> binaries.</p> </div> <div class="paragraph"> <p>In many cases, more than one binary can be produced for a component. These binaries may vary based on the tool chain used to build, the compiler/linker flags supplied, the dependencies provided, or additional source files provided. Each native binary produced for a component is referred to as a <em>variant</em>. Binary variants are discussed in detail below.</p> </div> </div> </div> <div class="sect1"> <h2 id="sec:parallel_compilation"><a class="anchor" href="#sec:parallel_compilation"></a><a class="link" href="#sec:parallel_compilation">Parallel Compilation</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Gradle uses the single build worker pool to concurrently compile and link native components, by default. No special configuration is required to enable concurrent building.</p> </div> <div class="paragraph"> <p>By default, the worker pool size is determined by the number of available processors on the build machine (as reported to the build JVM). To explicitly set the number of workers use the <code>--max-workers</code> command-line option or <code>org.gradle.workers.max</code> system property. There is generally no need to change this setting from its default.</p> </div> <div class="paragraph"> <p>The build worker pool is shared across all build tasks. This means that when using <a href="performance.html#parallel_execution">parallel project execution</a>, the maximum number of concurrent individual compilation operations does not increase. For example, if the build machine has 4 processing cores and 10 projects are compiling in parallel, Gradle will only use 4 total workers, not 40.</p> </div> </div> </div> <div class="sect1"> <h2 id="sec:building_a_library"><a class="anchor" href="#sec:building_a_library"></a><a class="link" href="#sec:building_a_library">Building a library</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>To build either a static or shared native library, you define a library component in the <code>components</code> container. The following sample defines a library called <code>hello</code>:</p> </div> <div class="sect2"> <h3 id="example_defining_a_library_component"><a class="anchor" href="#example_defining_a_library_component"></a><a class="link" href="#example_defining_a_library_component">Example: Defining a library component</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { hello(NativeLibrarySpec) } }</code></pre> </div> </div> <div class="paragraph"> <p>A library component is represented using <a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a>. Each library component can produce at least one shared library binary (<a href="../javadoc/org/gradle/nativeplatform/SharedLibraryBinarySpec.html">SharedLibraryBinarySpec</a>) and at least one static library binary (<a href="../javadoc/org/gradle/nativeplatform/StaticLibraryBinarySpec.html">StaticLibraryBinarySpec</a>).</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:building_an_executable"><a class="anchor" href="#sec:building_an_executable"></a><a class="link" href="#sec:building_an_executable">Building an executable</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>To build a native executable, you define an executable component in the <code>components</code> container. The following sample defines an executable called <code>main</code>:</p> </div> <div class="sect2"> <h3 id="example_defining_executable_components"><a class="anchor" href="#example_defining_executable_components"></a><a class="link" href="#example_defining_executable_components">Example: Defining executable components</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { main(NativeExecutableSpec) { sources { c.lib library: "hello" } } } }</code></pre> </div> </div> <div class="paragraph"> <p>An executable component is represented using <a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a>. Each executable component can produce at least one executable binary (<a href="../javadoc/org/gradle/nativeplatform/NativeExecutableBinarySpec.html">NativeExecutableBinarySpec</a>).</p> </div> <div class="paragraph"> <p>For each component defined, Gradle adds a <a href="../javadoc/org/gradle/language/base/FunctionalSourceSet.html">FunctionalSourceSet</a> with the same name. Each of these functional source sets will contain a language-specific source set for each of the languages supported by the project.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:dependents"><a class="anchor" href="#sec:dependents"></a><a class="link" href="#sec:dependents">Assembling or building dependents</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Sometimes, you may need to <em>assemble</em> (compile and link) or <em>build</em> (compile, link and test) a component or binary and its <em>dependents</em> (things that depend upon the component or binary). The native software model provides tasks that enable this capability. First, the <em>dependent components</em> report gives insight about the relationships between each component. Second, the <em>build and assemble dependents</em> tasks allow you to assemble or build a component and its dependents in one step.</p> </div> <div class="paragraph"> <p>In the following example, the build file defines <code>OpenSSL</code> as a dependency of <code>libUtil</code> and <code>libUtil</code> as a dependency of <code>LinuxApp</code> and <code>WindowsApp</code>. Test suites are treated similarly. Dependents can be thought of as reverse dependencies.</p> </div> <div class="imageblock"> <div class="content"> <img src="img/nativeDependents.png" alt="nativeDependents"> </div> <div class="title">Figure 1. Dependent Components Example</div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> By following the dependencies backwards, you can see <code>LinuxApp</code> and <code>WindowsApp</code> are <em>dependents</em> of <code>libUtil</code>. When <code>libUtil</code> is changed, Gradle will need to recompile or relink <code>LinuxApp</code> and <code>WindowsApp</code>. </td> </tr> </table> </div> <div class="paragraph"> <p>When you <em>assemble</em> dependents of a component, the component and all of its dependents are compiled and linked, including any test suite binaries. Gradle&#8217;s up-to-date checks are used to only compile or link if something has changed. For instance, if you have changed source files in a way that do not affect the headers of your project, Gradle will be able to skip compilation for dependent components and only need to re-link with the new library. Tests are not run when assembling a component.</p> </div> <div class="paragraph"> <p>When you <em>build</em> dependents of a component, the component and all of its dependent binaries are compiled, linked <em>and checked</em>. Checking components means running any <a href="#sec:check_tasks">check task</a> including executing any test suites, so tests <em>are</em> run when building a component.</p> </div> <div class="paragraph"> <p>In the following sections, we will demonstrate the usage of the <code>assembleDependents*</code>, <code>buildDependents*</code> and <code>dependentComponents</code> tasks with a sample build that contains a CUnit test suite. The build script for the sample is the following:</p> </div> <div class="sect2"> <h3 id="example_sample_build"><a class="anchor" href="#example_sample_build"></a><a class="link" href="#example_sample_build">Example: Sample build</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'c' id 'cunit-test-suite' } model { flavors { passing failing } platforms { x86 { if (operatingSystem.macOsX) { architecture "x64" } else { architecture "x86" } } } components { operators(NativeLibrarySpec) { targetPlatform "x86" } } testSuites { operatorsTest(CUnitTestSuiteSpec) { testing $.components.operators } } }</code></pre> </div> </div> </div> <div class="sect2"> <h3 id="sec:dependents_report"><a class="anchor" href="#sec:dependents_report"></a><a class="link" href="#sec:dependents_report">Dependent components report</a></h3> <div class="paragraph"> <p>Gradle provides a report that you can run from the command-line that shows a graph of components in your project and components that depend upon them. The following is an example of running <code>gradle dependentComponents</code> on the sample project:</p> </div> </div> <div class="sect2"> <h3 id="example_dependent_components_report"><a class="anchor" href="#example_dependent_components_report"></a><a class="link" href="#example_dependent_components_report">Example: Dependent components report</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle dependentComponents</code></strong></div> <div class="content"> <pre>&gt; gradle dependentComponents &gt; Task :dependentComponents ------------------------------------------------------------ Root project 'cunit' ------------------------------------------------------------ operators - Components that depend on native library 'operators' +--- operators:failingSharedLibrary +--- operators:failingStaticLibrary +--- operators:passingSharedLibrary \--- operators:passingStaticLibrary Some test suites were not shown, use --test-suites or --all to show them. BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> See <a href="../dsl/org.gradle.api.reporting.dependents.DependentComponentsReport.html">DependentComponentsReport</a> API documentation for more details. </td> </tr> </table> </div> <div class="paragraph"> <p>By default, non-buildable binaries and test suites are hidden from the report. The <code>dependentComponents</code> task provides options that allow you to see all dependents by using the <code>--all</code> option:</p> </div> </div> <div class="sect2"> <h3 id="example_dependent_components_report_2"><a class="anchor" href="#example_dependent_components_report_2"></a><a class="link" href="#example_dependent_components_report_2">Example: Dependent components report</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle dependentComponents --all</code></strong></div> <div class="content"> <pre>&gt; gradle dependentComponents --all &gt; Task :dependentComponents ------------------------------------------------------------ Root project 'cunit' ------------------------------------------------------------ operators - Components that depend on native library 'operators' +--- operators:failingSharedLibrary +--- operators:failingStaticLibrary | \--- operatorsTest:failingCUnitExe (t) +--- operators:passingSharedLibrary \--- operators:passingStaticLibrary \--- operatorsTest:passingCUnitExe (t) operatorsTest - Components that depend on Cunit test suite 'operatorsTest' +--- operatorsTest:failingCUnitExe (t) \--- operatorsTest:passingCUnitExe (t) (t) - Test suite binary BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> <div class="paragraph"> <p>Here is the corresponding report for the <code>operators</code> component, showing dependents of all its binaries:</p> </div> </div> <div class="sect2"> <h3 id="example_report_of_components_that_depends_on_the_operators_component"><a class="anchor" href="#example_report_of_components_that_depends_on_the_operators_component"></a><a class="link" href="#example_report_of_components_that_depends_on_the_operators_component">Example: Report of components that depends on the operators component</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle dependentComponents --component operators</code></strong></div> <div class="content"> <pre>&gt; gradle dependentComponents --component operators &gt; Task :dependentComponents ------------------------------------------------------------ Root project 'cunit' ------------------------------------------------------------ operators - Components that depend on native library 'operators' +--- operators:failingSharedLibrary +--- operators:failingStaticLibrary +--- operators:passingSharedLibrary \--- operators:passingStaticLibrary Some test suites were not shown, use --test-suites or --all to show them. BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> <div class="paragraph"> <p>Here is the corresponding report for the <code>operators</code> component, showing dependents of all its binaries, including test suites:</p> </div> </div> <div class="sect2"> <h3 id="example_report_of_components_that_depends_on_the_operators_component_including_test_suites"><a class="anchor" href="#example_report_of_components_that_depends_on_the_operators_component_including_test_suites"></a><a class="link" href="#example_report_of_components_that_depends_on_the_operators_component_including_test_suites">Example: Report of components that depends on the operators component, including test suites</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle dependentComponents --test-suites --component operators</code></strong></div> <div class="content"> <pre>&gt; gradle dependentComponents --test-suites --component operators &gt; Task :dependentComponents ------------------------------------------------------------ Root project 'cunit' ------------------------------------------------------------ operators - Components that depend on native library 'operators' +--- operators:failingSharedLibrary +--- operators:failingStaticLibrary | \--- operatorsTest:failingCUnitExe (t) +--- operators:passingSharedLibrary \--- operators:passingStaticLibrary \--- operatorsTest:passingCUnitExe (t) (t) - Test suite binary BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> <div class="paragraph"> <p>Furthermore, the <code>--non-binaries</code> option shows non-buildable binaries in the report, <code>--no-non-buildable</code> hides them. Similarly, the <code>--test-suites</code> option shows test suites and <code>--no-test-suites</code> hides them. The option <code>--no-all</code> hides both non-buildable binaries and test suites from the report.</p> </div> </div> <div class="sect2"> <h3 id="sec:assemble_dependents"><a class="anchor" href="#sec:assemble_dependents"></a><a class="link" href="#sec:assemble_dependents">Assembling dependents</a></h3> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a>, Gradle will create a task named <code>assembleDependents<em>${component.name}${binary.variant}</em></code> that <em>assembles</em> (compile and link) the binary and all of its dependent binaries.</p> </div> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeComponentSpec.html">NativeComponentSpec</a>, Gradle will create a task named <code>assembleDependents<em>${component.name}</em></code> that <em>assembles</em> all the binaries of the component and all of their dependent binaries.</p> </div> <div class="paragraph"> <p>For example, to assemble the dependents of the "passing" flavor of the "static" library binary of the "operators" component, you would run the <code>assembleDependentsOperatorsPassingStaticLibrary</code> task:</p> </div> </div> <div class="sect2"> <h3 id="example_assemble_components_that_depends_on_the_passingstatic_binary_of_the_operators_component"><a class="anchor" href="#example_assemble_components_that_depends_on_the_passingstatic_binary_of_the_operators_component"></a><a class="link" href="#example_assemble_components_that_depends_on_the_passingstatic_binary_of_the_operators_component">Example: Assemble components that depends on the passing/static binary of the operators component</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle assembleDependentsOperatorsPassingStaticLibrary --max-workers=1</code></strong></div> <div class="content"> <pre>&gt; gradle assembleDependentsOperatorsPassingStaticLibrary --max-workers=1 &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsC &gt; Task :operatorsTestCUnitLauncher &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsTestC &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsTestCunitLauncher &gt; Task :linkOperatorsTestPassingCUnitExe &gt; Task :operatorsTestPassingCUnitExe &gt; Task :assembleDependentsOperatorsTestPassingCUnitExe &gt; Task :compileOperatorsPassingStaticLibraryOperatorsC &gt; Task :createOperatorsPassingStaticLibrary &gt; Task :operatorsPassingStaticLibrary &gt; Task :assembleDependentsOperatorsPassingStaticLibrary BUILD SUCCESSFUL in 0s 7 actionable tasks: 7 executed</pre> </div> </div> <div class="paragraph"> <p>In the output above, the targeted binary gets assembled as well as the test suite binary that depends on it.</p> </div> <div class="paragraph"> <p>You can also assemble <em>all</em> of the dependents of a component (i.e. of all its binaries/variants) using the corresponding component task, e.g. <code>assembleDependentsOperators</code>. This is useful if you have many combinations of build types, flavors and platforms and want to assemble all of them.</p> </div> </div> <div class="sect2"> <h3 id="sec:build_dependents"><a class="anchor" href="#sec:build_dependents"></a><a class="link" href="#sec:build_dependents">Building dependents</a></h3> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a>, Gradle will create a task named <code>buildDependents<em>${component.name}${binary.variant}</em></code> that <em>builds</em> (compile, link and check) the binary and all of its dependent binaries.</p> </div> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeComponentSpec.html">NativeComponentSpec</a>, Gradle will create a task named <code>buildDependents<em>${component.name}</em></code> that <em>builds</em> all the binaries of the component and all of their dependent binaries.</p> </div> <div class="paragraph"> <p>For example, to build the dependents of the "passing" flavor of the "static" library binary of the "operators" component, you would run the <code>buildDependentsOperatorsPassingStaticLibrary</code> task:</p> </div> </div> <div class="sect2"> <h3 id="example_build_components_that_depends_on_the_passingstatic_binary_of_the_operators_component"><a class="anchor" href="#example_build_components_that_depends_on_the_passingstatic_binary_of_the_operators_component"></a><a class="link" href="#example_build_components_that_depends_on_the_passingstatic_binary_of_the_operators_component">Example: Build components that depends on the passing/static binary of the operators component</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle buildDependentsOperatorsPassingStaticLibrary --max-workers=1</code></strong></div> <div class="content"> <pre>&gt; gradle buildDependentsOperatorsPassingStaticLibrary --max-workers=1 &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsC &gt; Task :operatorsTestCUnitLauncher &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsTestC &gt; Task :compileOperatorsTestPassingCUnitExeOperatorsTestCunitLauncher &gt; Task :linkOperatorsTestPassingCUnitExe &gt; Task :operatorsTestPassingCUnitExe &gt; Task :installOperatorsTestPassingCUnitExe &gt; Task :runOperatorsTestPassingCUnitExe &gt; Task :checkOperatorsTestPassingCUnitExe &gt; Task :buildDependentsOperatorsTestPassingCUnitExe &gt; Task :compileOperatorsPassingStaticLibraryOperatorsC &gt; Task :createOperatorsPassingStaticLibrary &gt; Task :operatorsPassingStaticLibrary &gt; Task :buildDependentsOperatorsPassingStaticLibrary BUILD SUCCESSFUL in 0s 9 actionable tasks: 9 executed</pre> </div> </div> <div class="paragraph"> <p>In the output above, the targeted binary as well as the test suite binary that depends on it are built and the test suite has run.</p> </div> <div class="paragraph"> <p>You can also build <em>all</em> of the dependents of a component (i.e. of all its binaries/variants) using the corresponding component task, e.g. <code>buildDependentsOperators</code>.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:native_tasks"><a class="anchor" href="#sec:native_tasks"></a><a class="link" href="#sec:native_tasks">Tasks</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> that can be produced by a build, a single <em>lifecycle task</em> is constructed that can be used to create that binary, together with a set of other tasks that do the actual work of compiling, linking or assembling the binary.</p> </div> <div class="dlist"> <dl> <dt class="hdlist1"><code><em>${component.name}</em>Executable</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeExecutableBinarySpec.html">NativeExecutableBinarySpec</a></p> </dd> <dt class="hdlist1">Location of created binary</dt> <dd> <p><code><em>${project.layout.buildDirectory}</em>/exe/<em>${component.name}</em>/<em>${component.name}</em></code></p> </dd> </dl> </div> </dd> <dt class="hdlist1"><code><em>${component.name}</em>SharedLibrary</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/SharedLibraryBinarySpec.html">SharedLibraryBinarySpec</a></p> </dd> <dt class="hdlist1">Location of created binary</dt> <dd> <p><code><em>${project.layout.buildDirectory}</em>/libs/<em>${component.name}</em>/shared/lib<em>${component.name}</em>.so</code></p> </dd> </dl> </div> </dd> <dt class="hdlist1"><code><em>${component.name}</em>StaticLibrary</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/StaticLibraryBinarySpec.html">StaticLibraryBinarySpec</a></p> </dd> <dt class="hdlist1">Location of created binary</dt> <dd> <p><code><em>${project.layout.buildDirectory}</em>/libs/<em>${component.name}</em>/static/<em>${component.name}</em>.a</code></p> </dd> </dl> </div> </dd> </dl> </div> <div class="sect2"> <h3 id="sec:check_tasks"><a class="anchor" href="#sec:check_tasks"></a><a class="link" href="#sec:check_tasks">Check tasks</a></h3> <div class="paragraph"> <p>For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> that can be produced by a build, a single <em>check task</em> is constructed that can be used to assemble and check that binary.</p> </div> <div class="dlist"> <dl> <dt class="hdlist1"><code>check<em>${component.name}</em>Executable</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeExecutableBinarySpec.html">NativeExecutableBinarySpec</a></p> </dd> </dl> </div> </dd> <dt class="hdlist1"><code>check<em>${component.name}</em>SharedLibrary</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/SharedLibraryBinarySpec.html">SharedLibraryBinarySpec</a></p> </dd> </dl> </div> </dd> <dt class="hdlist1"><code>check<em>${component.name}</em>StaticLibrary</code></dt> <dd> <div class="dlist"> <dl> <dt class="hdlist1">Component Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a></p> </dd> <dt class="hdlist1">Native Binary Type</dt> <dd> <p><a href="../javadoc/org/gradle/nativeplatform/SharedLibraryBinarySpec.html">SharedLibraryBinarySpec</a></p> </dd> </dl> </div> </dd> </dl> </div> <div class="paragraph"> <p>The built-in <code>check</code> task depends on all the <em>check tasks</em> for binaries in the project. Without either <a href="#native_binaries:cunit">CUnit</a> or <a href="#native_binaries:google_test">GoogleTest</a> plugins, the binary check task only depends on the <em>lifecycle task</em> that assembles the binary, see <a href="#sec:native_tasks">Native tasks</a>.</p> </div> <div class="paragraph"> <p>When the <a href="#native_binaries:cunit">CUnit</a> or <a href="#native_binaries:google_test">GoogleTest</a> plugins are applied, the task that executes the test suites for a component are automatically wired to the appropriate <em>check task</em>.</p> </div> <div class="paragraph"> <p>You can also add custom check tasks as follows:</p> </div> </div> <div class="sect2"> <h3 id="example_adding_a_custom_check_task"><a class="anchor" href="#example_adding_a_custom_check_task"></a><a class="link" href="#example_adding_a_custom_check_task">Example: Adding a custom check task</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id "cpp" } // You don't need to apply the plugin below if you're already using CUnit or GoogleTest support apply plugin: TestingModelBasePlugin tasks.register('myCustomCheck') { doLast { println 'Executing my custom check' } } model { components { hello(NativeLibrarySpec) { binaries.all { // Register our custom check task to all binaries of this component checkedBy $.tasks.myCustomCheck } } } }</code></pre> </div> </div> <div class="paragraph"> <p>Now, running <code>check</code> or any of the <em>check tasks</em> for the <code>hello</code> binaries will run the custom check task:</p> </div> </div> <div class="sect2"> <h3 id="example_running_checks_for_a_given_binary"><a class="anchor" href="#example_running_checks_for_a_given_binary"></a><a class="link" href="#example_running_checks_for_a_given_binary">Example: Running checks for a given binary</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle checkHelloSharedLibrary</code></strong></div> <div class="content"> <pre>&gt; gradle checkHelloSharedLibrary &gt; Task :myCustomCheck Executing my custom check &gt; Task :checkHelloSharedLibrary BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> </div> <div class="sect2"> <h3 id="sec:working_with_shared_libraries"><a class="anchor" href="#sec:working_with_shared_libraries"></a><a class="link" href="#sec:working_with_shared_libraries">Working with shared libraries</a></h3> <div class="paragraph"> <p>For each executable binary produced, the <code>cpp</code> plugin provides an <code>install${binary.name}</code> task, which creates a development install of the executable, along with the shared libraries it requires. This allows you to run the executable without needing to install the shared libraries in their final locations.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:finding_out_more_about_your_project"><a class="anchor" href="#sec:finding_out_more_about_your_project"></a><a class="link" href="#sec:finding_out_more_about_your_project">Finding out more about your project</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Gradle provides a report that you can run from the command-line that shows some details about the components and binaries that your project produces. To use this report, just run <code>gradle components</code>. Below is an example of running this report for one of the sample projects:</p> </div> <div class="sect2"> <h3 id="example_the_components_report"><a class="anchor" href="#example_the_components_report"></a><a class="link" href="#example_the_components_report">Example: The components report</a></h3> <div class="listingblock"> <div class="title">Output of <strong><code>gradle components</code></strong></div> <div class="content"> <pre>&gt; gradle components &gt; Task :components ------------------------------------------------------------ Root project 'cpp' ------------------------------------------------------------ Native library 'hello' ---------------------- Source sets C++ source 'hello:cpp' srcDir: src/hello/cpp Binaries Shared library 'hello:sharedLibrary' build using task: :helloSharedLibrary build type: build type 'debug' flavor: flavor 'default' target platform: platform 'current' tool chain: Tool chain 'clang' (Clang) shared library file: build/libs/hello/shared/libhello.dylib Static library 'hello:staticLibrary' build using task: :helloStaticLibrary build type: build type 'debug' flavor: flavor 'default' target platform: platform 'current' tool chain: Tool chain 'clang' (Clang) static library file: build/libs/hello/static/libhello.a Native executable 'main' ------------------------ Source sets C++ source 'main:cpp' srcDir: src/main/cpp Binaries Executable 'main:executable' build using task: :mainExecutable install using task: :installMainExecutable build type: build type 'debug' flavor: flavor 'default' target platform: platform 'current' tool chain: Tool chain 'clang' (Clang) executable file: build/exe/main/main Note: currently not all plugins register their components, so some components may not be visible here. BUILD SUCCESSFUL in 0s 1 actionable task: 1 executed</pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:languages"><a class="anchor" href="#native_binaries:languages"></a><a class="link" href="#native_binaries:languages">Language support</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Presently, Gradle supports building native software from any combination of source languages listed below. A native binary project will contain one or more named <code>FunctionalSourceSet</code> instances (e.g. 'main', 'test', etc), each of which can contain <code>LanguageSourceSet</code>s containing source files, one for each language.</p> </div> <div class="ulist"> <ul> <li> <p>C</p> </li> <li> <p>C++</p> </li> <li> <p>Objective-C</p> </li> <li> <p>Objective-C++</p> </li> <li> <p>Assembly</p> </li> <li> <p>Windows resources</p> </li> </ul> </div> <div class="sect2"> <h3 id="sec:cpp_sources"><a class="anchor" href="#sec:cpp_sources"></a><a class="link" href="#sec:cpp_sources">C++ sources</a></h3> <div class="paragraph"> <p>C++ language support is provided by means of the <code>'cpp'</code> plugin.</p> </div> </div> <div class="sect2"> <h3 id="example_the_cpp_plugin"><a class="anchor" href="#example_the_cpp_plugin"></a><a class="link" href="#example_the_cpp_plugin">Example: The 'cpp' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'cpp' }</code></pre> </div> </div> <div class="paragraph"> <p>C++ sources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.cpp.CppSourceSet.html">CppSourceSet</a>, which defines a set of C++ source files and optionally a set of exported header files (for a library). By default, for any named component the <a href="../dsl/org.gradle.language.cpp.CppSourceSet.html">CppSourceSet</a> contains <code>.cpp</code> source files in <code>src/${name}/cpp</code>, and header files in <code>src/${name}/headers</code>.</p> </div> <div class="paragraph"> <p>While the <code>cpp</code> plugin defines these default locations for each <a href="../dsl/org.gradle.language.cpp.CppSourceSet.html">CppSourceSet</a>, it is possible to extend or override these defaults to allow for a different project layout.</p> </div> </div> <div class="sect2"> <h3 id="example_c_source_set"><a class="anchor" href="#example_c_source_set"></a><a class="link" href="#example_c_source_set">Example: C++ source set</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">sources { cpp { source { srcDir "src/source" include "**/*.cpp" } } }</code></pre> </div> </div> <div class="paragraph"> <p>For a library named 'main', header files in <code>src/main/headers</code> are considered the "public" or "exported" headers. Header files that should not be exported should be placed inside the <code>src/main/cpp</code> directory (though be aware that such header files should always be referenced in a manner relative to the file including them).</p> </div> </div> <div class="sect2"> <h3 id="sec:c_sources"><a class="anchor" href="#sec:c_sources"></a><a class="link" href="#sec:c_sources">C sources</a></h3> <div class="paragraph"> <p>C language support is provided by means of the <code>'c'</code> plugin.</p> </div> </div> <div class="sect2"> <h3 id="example_the_c_plugin"><a class="anchor" href="#example_the_c_plugin"></a><a class="link" href="#example_the_c_plugin">Example: The 'c' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'c' }</code></pre> </div> </div> <div class="paragraph"> <p>C sources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.c.CSourceSet.html">CSourceSet</a>, which defines a set of C source files and optionally a set of exported header files (for a library). By default, for any named component the <a href="../dsl/org.gradle.language.c.CSourceSet.html">CSourceSet</a> contains <code>.c</code> source files in <code>src/${name}/c</code>, and header files in <code>src/${name}/headers</code>.</p> </div> <div class="paragraph"> <p>While the <code>c</code> plugin defines these default locations for each <a href="../dsl/org.gradle.language.c.CSourceSet.html">CSourceSet</a>, it is possible to extend or override these defaults to allow for a different project layout.</p> </div> </div> <div class="sect2"> <h3 id="example_c_source_set_2"><a class="anchor" href="#example_c_source_set_2"></a><a class="link" href="#example_c_source_set_2">Example: C source set</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">sources { c { source { srcDir "src/source" include "**/*.c" } exportedHeaders { srcDir "src/include" } } }</code></pre> </div> </div> <div class="paragraph"> <p>For a library named 'main', header files in <code>src/main/headers</code> are considered the "public" or "exported" headers. Header files that should not be exported should be placed inside the <code>src/main/c</code> directory (though be aware that such header files should always be referenced in a manner relative to the file including them).</p> </div> </div> <div class="sect2"> <h3 id="sec:assembler_sources"><a class="anchor" href="#sec:assembler_sources"></a><a class="link" href="#sec:assembler_sources">Assembler sources</a></h3> <div class="paragraph"> <p>Assembly language support is provided by means of the <code>'assembler'</code> plugin.</p> </div> </div> <div class="sect2"> <h3 id="example_the_assembler_plugin"><a class="anchor" href="#example_the_assembler_plugin"></a><a class="link" href="#example_the_assembler_plugin">Example: The 'assembler' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'assembler' }</code></pre> </div> </div> <div class="paragraph"> <p>Assembler sources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.assembler.AssemblerSourceSet.html">AssemblerSourceSet</a>, which defines a set of Assembler source files. By default, for any named component the <a href="../dsl/org.gradle.language.assembler.AssemblerSourceSet.html">AssemblerSourceSet</a> contains <code>.s</code> source files under <code>src/${name}/asm</code>.</p> </div> </div> <div class="sect2"> <h3 id="sec:objectivec_sources"><a class="anchor" href="#sec:objectivec_sources"></a><a class="link" href="#sec:objectivec_sources">Objective-C sources</a></h3> <div class="paragraph"> <p>Objective-C language support is provided by means of the <code>'objective-c'</code> plugin.</p> </div> </div> <div class="sect2"> <h3 id="example_the_objective_c_plugin"><a class="anchor" href="#example_the_objective_c_plugin"></a><a class="link" href="#example_the_objective_c_plugin">Example: The 'objective-c' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'objective-c' }</code></pre> </div> </div> <div class="paragraph"> <p>Objective-C sources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.objectivec.ObjectiveCSourceSet.html">ObjectiveCSourceSet</a>, which defines a set of Objective-C source files. By default, for any named component the <a href="../dsl/org.gradle.language.objectivec.ObjectiveCSourceSet.html">ObjectiveCSourceSet</a> contains <code>.m</code> source files under <code>src/${name}/objectiveC</code>.</p> </div> </div> <div class="sect2"> <h3 id="sec:objectivecpp_sources"><a class="anchor" href="#sec:objectivecpp_sources"></a><a class="link" href="#sec:objectivecpp_sources">Objective-C++ sources</a></h3> <div class="paragraph"> <p>Objective-C++ language support is provided by means of the <code>'objective-cpp'</code> plugin.</p> </div> </div> <div class="sect2"> <h3 id="example_the_objective_cpp_plugin"><a class="anchor" href="#example_the_objective_cpp_plugin"></a><a class="link" href="#example_the_objective_cpp_plugin">Example: The 'objective-cpp' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'objective-cpp' }</code></pre> </div> </div> <div class="paragraph"> <p>Objective-C++ sources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.objectivecpp.ObjectiveCppSourceSet.html">ObjectiveCppSourceSet</a>, which defines a set of Objective-C++ source files. By default, for any named component the <a href="../dsl/org.gradle.language.objectivecpp.ObjectiveCppSourceSet.html">ObjectiveCppSourceSet</a> contains <code>.mm</code> source files under <code>src/${name}/objectiveCpp</code>.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:configuring_the_compiler_assembler_and_linker"><a class="anchor" href="#sec:configuring_the_compiler_assembler_and_linker"></a><a class="link" href="#sec:configuring_the_compiler_assembler_and_linker">Configuring the compiler, assembler and linker</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Each binary to be produced is associated with a set of compiler and linker settings, which include command-line arguments as well as macro definitions. These settings can be applied to all binaries, an individual binary, or selectively to a group of binaries based on some criteria.</p> </div> <div class="sect2"> <h3 id="example_settings_that_apply_to_all_binaries"><a class="anchor" href="#example_settings_that_apply_to_all_binaries"></a><a class="link" href="#example_settings_that_apply_to_all_binaries">Example: Settings that apply to all binaries</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { binaries { all { // Define a preprocessor macro for every binary cppCompiler.define "NDEBUG" // Define toolchain-specific compiler and linker options if (toolChain in Gcc) { cppCompiler.args "-O2", "-fno-access-control" linker.args "-Xlinker", "-S" } if (toolChain in VisualCpp) { cppCompiler.args "/Zi" linker.args "/DEBUG" } } } }</code></pre> </div> </div> <div class="paragraph"> <p>Each binary is associated with a particular <a href="../javadoc/org/gradle/nativeplatform/toolchain/NativeToolChain.html">NativeToolChain</a>, allowing settings to be targeted based on this value.</p> </div> <div class="paragraph"> <p>It is easy to apply settings to all binaries of a particular type:</p> </div> </div> <div class="sect2"> <h3 id="example_settings_that_apply_to_all_shared_libraries"><a class="anchor" href="#example_settings_that_apply_to_all_shared_libraries"></a><a class="link" href="#example_settings_that_apply_to_all_shared_libraries">Example: Settings that apply to all shared libraries</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">// For any shared library binaries built with Visual C++, // define the DLL_EXPORT macro model { binaries { withType(SharedLibraryBinarySpec) { if (toolChain in VisualCpp) { cCompiler.args "/Zi" cCompiler.define "DLL_EXPORT" } } } }</code></pre> </div> </div> <div class="paragraph"> <p>Furthermore, it is possible to specify settings that apply to all binaries produced for a particular <code>executable</code> or <code>library</code> component:</p> </div> </div> <div class="sect2"> <h3 id="example_settings_that_apply_to_all_binaries_produced_for_the_main_executable_component"><a class="anchor" href="#example_settings_that_apply_to_all_binaries_produced_for_the_main_executable_component"></a><a class="link" href="#example_settings_that_apply_to_all_binaries_produced_for_the_main_executable_component">Example: Settings that apply to all binaries produced for the 'main' executable component</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { main(NativeExecutableSpec) { targetPlatform "x86" binaries.all { if (toolChain in VisualCpp) { sources { platformAsm(AssemblerSourceSet) { source.srcDir "src/main/asm_i386_masm" } } assembler.args "/Zi" } else { sources { platformAsm(AssemblerSourceSet) { source.srcDir "src/main/asm_i386_gcc" } } assembler.args "-g" } } } } }</code></pre> </div> </div> <div class="paragraph"> <p>The example above will apply the supplied configuration to all <code>executable</code> binaries built.</p> </div> <div class="paragraph"> <p>Similarly, settings can be specified to target binaries for a component that are of a particular type: e.g. all shared libraries for the main library component.</p> </div> </div> <div class="sect2"> <h3 id="example_settings_that_apply_only_to_shared_libraries_produced_for_the_main_library_component"><a class="anchor" href="#example_settings_that_apply_only_to_shared_libraries_produced_for_the_main_library_component"></a><a class="link" href="#example_settings_that_apply_only_to_shared_libraries_produced_for_the_main_library_component">Example: Settings that apply only to shared libraries produced for the 'main' library component</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { main(NativeLibrarySpec) { binaries.withType(SharedLibraryBinarySpec) { // Define a preprocessor macro that only applies to shared libraries cppCompiler.define "DLL_EXPORT" } } } }</code></pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:windows-resources"><a class="anchor" href="#native_binaries:windows-resources"></a><a class="link" href="#native_binaries:windows-resources">Windows Resources</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>When using the <a href="../dsl/org.gradle.nativeplatform.toolchain.VisualCpp.html">VisualCpp</a> tool chain, Gradle is able to compile Window Resource (<code>rc</code>) files and link them into a native binary. This functionality is provided by the <code>'windows-resources'</code> plugin.</p> </div> <div class="sect2"> <h3 id="example_the_windows_resources_plugin"><a class="anchor" href="#example_the_windows_resources_plugin"></a><a class="link" href="#example_the_windows_resources_plugin">Example: The 'windows-resources' plugin</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'windows-resources' }</code></pre> </div> </div> <div class="paragraph"> <p>Windows resources to be included in a native binary are provided via a <a href="../dsl/org.gradle.language.rc.WindowsResourceSet.html">WindowsResourceSet</a>, which defines a set of Windows Resource source files. By default, for any named component the <a href="../dsl/org.gradle.language.rc.WindowsResourceSet.html">WindowsResourceSet</a> contains <code>.rc</code> source files under <code>src/${name}/rc</code>.</p> </div> <div class="paragraph"> <p>As with other source types, you can configure the location of the windows resources that should be included in the binary.</p> </div> </div> <div class="sect2"> <h3 id="example_configuring_the_location_of_windows_resource_sources"><a class="anchor" href="#example_configuring_the_location_of_windows_resource_sources"></a><a class="link" href="#example_configuring_the_location_of_windows_resource_sources">Example: Configuring the location of Windows resource sources</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build-resource-only-dll.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">sources { rc { source { srcDirs "src/hello/rc" } exportedHeaders { srcDirs "src/hello/headers" } } }</code></pre> </div> </div> <div class="paragraph"> <p>You are able to construct a resource-only library by providing Windows Resource sources with no other language sources, and configure the linker as appropriate:</p> </div> </div> <div class="sect2"> <h3 id="example_building_a_resource_only_dll"><a class="anchor" href="#example_building_a_resource_only_dll"></a><a class="link" href="#example_building_a_resource_only_dll">Example: Building a resource-only dll</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build-resource-only-dll.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { helloRes(NativeLibrarySpec) { binaries.all { rcCompiler.args "/v" linker.args "/noentry", "/machine:x86" } sources { rc { source { srcDirs "src/hello/rc" } exportedHeaders { srcDirs "src/hello/headers" } } } } } }</code></pre> </div> </div> <div class="paragraph"> <p>The example above also demonstrates the mechanism of passing extra command-line arguments to the resource compiler. The <code>rcCompiler</code> extension is of type <a href="../javadoc/org/gradle/nativeplatform/PreprocessingTool.html">PreprocessingTool</a>.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="sec:library_dependencies"><a class="anchor" href="#sec:library_dependencies"></a><a class="link" href="#sec:library_dependencies">Library Dependencies</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Dependencies for native components are binary libraries that export header files. The header files are used during compilation, with the compiled binary dependency being used during linking and execution. Header files should be organized into subdirectories to prevent clashes of commonly named headers. For instance, if your <code>mylib</code> project has a <code>logging.h</code> header, it will make it less likely the wrong header is used if you include it as <code>"mylib/logging.h"</code> instead of <code>"logging.h"</code>.</p> </div> <div class="sect2"> <h3 id="sec:dependencies_within_the_same_project"><a class="anchor" href="#sec:dependencies_within_the_same_project"></a><a class="link" href="#sec:dependencies_within_the_same_project">Dependencies within the same project</a></h3> <div class="paragraph"> <p>A set of sources may depend on header files provided by another binary component within the same project. A common example is a native executable component that uses functions provided by a separate native library component.</p> </div> <div class="paragraph"> <p>Such a library dependency can be added to a source set associated with the <code>executable</code> component:</p> </div> </div> <div class="sect2"> <h3 id="example_providing_a_library_dependency_to_the_source_set"><a class="anchor" href="#example_providing_a_library_dependency_to_the_source_set"></a><a class="link" href="#example_providing_a_library_dependency_to_the_source_set">Example: Providing a library dependency to the source set</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">sources { cpp { lib library: "hello" } }</code></pre> </div> </div> <div class="paragraph"> <p>Alternatively, a library dependency can be provided directly to the <code>NativeExecutableBinarySpec</code> for the <code>executable</code>.</p> </div> </div> <div class="sect2"> <h3 id="example_providing_a_library_dependency_to_the_binary"><a class="anchor" href="#example_providing_a_library_dependency_to_the_binary"></a><a class="link" href="#example_providing_a_library_dependency_to_the_binary">Example: Providing a library dependency to the binary</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { hello(NativeLibrarySpec) { sources { c { source { srcDir "src/source" include "**/*.c" } exportedHeaders { srcDir "src/include" } } } } main(NativeExecutableSpec) { sources { cpp { source { srcDir "src/source" include "**/*.cpp" } } } binaries.all { // Each executable binary produced uses the 'hello' static library binary lib library: 'hello', linkage: 'static' } } } }</code></pre> </div> </div> </div> <div class="sect2"> <h3 id="sec:project_dependencies"><a class="anchor" href="#sec:project_dependencies"></a><a class="link" href="#sec:project_dependencies">Project Dependencies</a></h3> <div class="paragraph"> <p>For a component produced in a different Gradle project, the notation is similar.</p> </div> </div> <div class="sect2"> <h3 id="example_declaring_project_dependencies"><a class="anchor" href="#example_declaring_project_dependencies"></a><a class="link" href="#example_declaring_project_dependencies">Example: Declaring project dependencies</a></h3> <div class="listingblock multi-language-sample"> <div class="title">lib/build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'cpp' } model { components { main(NativeLibrarySpec) } // For any shared library binaries built with Visual C++, // define the DLL_EXPORT macro binaries { withType(SharedLibraryBinarySpec) { if (toolChain in VisualCpp) { cppCompiler.define "DLL_EXPORT" } } } }</code></pre> </div> </div> <div class="listingblock multi-language-sample"> <div class="title">exe/build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'cpp' } model { components { main(NativeExecutableSpec) { sources { cpp { lib project: ':lib', library: 'main' } } } } }</code></pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:preCompiledHeaders"><a class="anchor" href="#native_binaries:preCompiledHeaders"></a><a class="link" href="#native_binaries:preCompiledHeaders">Precompiled Headers</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Precompiled headers are a performance optimization that reduces the cost of compiling widely used headers multiple times. This feature <em>precompiles</em> a header such that the compiled object file can be reused when compiling each source file rather than recompiling the header each time. This support is available for C, C++, Objective-C, and Objective-C++ builds.</p> </div> <div class="paragraph"> <p>To configure a precompiled header, first a header file needs to be defined that includes all of the headers that should be precompiled. It must be specified as the first included header in every source file where the precompiled header should be used. It is assumed that this header file, and any headers it contains, make use of header guards so that they can be included in an idempotent manner. If header guards are not used in a header file, it is possible the header could be compiled more than once and could potentially lead to a broken build.</p> </div> <div class="sect2"> <h3 id="example_creating_a_precompiled_header_file"><a class="anchor" href="#example_creating_a_precompiled_header_file"></a><a class="link" href="#example_creating_a_precompiled_header_file">Example: Creating a precompiled header file</a></h3> <div class="listingblock multi-language-sample"> <div class="title">src/hello/headers/pch.h</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="c">#ifndef PCH_H #define PCH_H #include &lt;iostream&gt; #include "hello.h" #endif</code></pre> </div> </div> </div> <div class="sect2"> <h3 id="example_including_a_precompiled_header_file_in_a_source_file"><a class="anchor" href="#example_including_a_precompiled_header_file_in_a_source_file"></a><a class="link" href="#example_including_a_precompiled_header_file_in_a_source_file">Example: Including a precompiled header file in a source file</a></h3> <div class="listingblock multi-language-sample"> <div class="title">src/hello/cpp/hello.cpp</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="cpp">#include "pch.h" void LIB_FUNC Greeter::hello () { std::cout &lt;&lt; "Hello world!" &lt;&lt; std::endl; }</code></pre> </div> </div> <div class="paragraph"> <p>Precompiled headers are specified on a source set. Only one precompiled header file can be specified on a given source set and will be applied to all source files that declare it as the first include. If a source files does not include this header file as the first header, the file will be compiled in the normal manner (without making use of the precompiled header object file). The string provided should be the same as that which is used in the "#include" directive in the source files.</p> </div> </div> <div class="sect2"> <h3 id="example_configuring_a_precompiled_header"><a class="anchor" href="#example_configuring_a_precompiled_header"></a><a class="link" href="#example_configuring_a_precompiled_header">Example: Configuring a precompiled header</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { hello(NativeLibrarySpec) { sources { cpp { preCompiledHeader "pch.h" } } } } }</code></pre> </div> </div> <div class="paragraph"> <p>A precompiled header must be included in the same way for all files that use it. Usually, this means the header file should exist in the source set "headers" directory or in a directory included on the compiler include path.</p> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:variants"><a class="anchor" href="#native_binaries:variants"></a><a class="link" href="#native_binaries:variants">Native Binary Variants</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>For each executable or library defined, Gradle is able to build a number of different native binary variants. Examples of different variants include debug vs release binaries, 32-bit vs 64-bit binaries, and binaries produced with different custom preprocessor flags.</p> </div> <div class="paragraph"> <p>Binaries produced by Gradle can be differentiated on <a href="#native_binaries:build_type">build type</a>, <a href="#native_binaries:platform">platform</a>, and <a href="#native_binaries:flavor">flavor</a>. For each of these 'variant dimensions', it is possible to specify a set of available values as well as target each component at one, some or all of these. For example, a plugin may define a range of support platforms, but you may choose to only target Windows-x86 for a particular component.</p> </div> <div class="sect2"> <h3 id="native_binaries:build_type"><a class="anchor" href="#native_binaries:build_type"></a><a class="link" href="#native_binaries:build_type">Build types</a></h3> <div class="paragraph"> <p>A <code>build type</code> determines various non-functional aspects of a binary, such as whether debug information is included, or what optimisation level the binary is compiled with. Typical build types are 'debug' and 'release', but a project is free to define any set of build types.</p> </div> </div> <div class="sect2"> <h3 id="example_defining_build_types"><a class="anchor" href="#example_defining_build_types"></a><a class="link" href="#example_defining_build_types">Example: Defining build types</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { buildTypes { debug release } }</code></pre> </div> </div> <div class="paragraph"> <p>If no build types are defined in a project, then a single, default build type called 'debug' is added.</p> </div> <div class="paragraph"> <p>For a build type, a Gradle project will typically define a set of compiler/linker flags per tool chain.</p> </div> </div> <div class="sect2"> <h3 id="example_configuring_debug_binaries"><a class="anchor" href="#example_configuring_debug_binaries"></a><a class="link" href="#example_configuring_debug_binaries">Example: Configuring debug binaries</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { binaries { all { if (toolChain in Gcc &amp;&amp; buildType == buildTypes.debug) { cppCompiler.args "-g" } if (toolChain in VisualCpp &amp;&amp; buildType == buildTypes.debug) { cppCompiler.args '/Zi' cppCompiler.define 'DEBUG' linker.args '/DEBUG' } } } }</code></pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> At this stage, it is completely up to the build script to configure the relevant compiler/linker flags for each build type. Future versions of Gradle will automatically include the appropriate debug flags for any 'debug' build type, and may be aware of various levels of optimisation as well. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="native_binaries:platform"><a class="anchor" href="#native_binaries:platform"></a><a class="link" href="#native_binaries:platform">Platform</a></h3> <div class="paragraph"> <p>An executable or library can be built to run on different operating systems and cpu architectures, with a variant being produced for each platform. Gradle defines each OS/architecture combination as a <a href="../dsl/org.gradle.nativeplatform.platform.NativePlatform.html">NativePlatform</a>, and a project may define any number of platforms. If no platforms are defined in a project, then a single, default platform 'current' is added.</p> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> <div class="paragraph"> <p>Presently, a <code>Platform</code> consists of a defined operating system and architecture. As we continue to develop the native binary support in Gradle, the concept of Platform will be extended to include things like C-runtime version, Windows SDK, ABI, etc. Sophisticated builds may use the extensibility of Gradle to apply additional attributes to each platform, which can then be queried to specify particular includes, preprocessor macros or compiler arguments for a native binary.</p> </div> </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="example_defining_platforms"><a class="anchor" href="#example_defining_platforms"></a><a class="link" href="#example_defining_platforms">Example: Defining platforms</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { platforms { x86 { architecture "x86" } x64 { architecture "x86_64" } itanium { architecture "ia-64" } } }</code></pre> </div> </div> <div class="paragraph"> <p>For a given variant, Gradle will attempt to find a <a href="../javadoc/org/gradle/nativeplatform/toolchain/NativeToolChain.html">NativeToolChain</a> that is able to build for the target platform. Available tool chains are searched in the order defined. See the <a href="#native_binaries:tool_chain">tool chains</a> section below for more details.</p> </div> </div> <div class="sect2"> <h3 id="native_binaries:flavor"><a class="anchor" href="#native_binaries:flavor"></a><a class="link" href="#native_binaries:flavor">Flavor</a></h3> <div class="paragraph"> <p>Each component can have a set of named <code>flavors</code>, and a separate binary variant can be produced for each flavor. While the <code>build type</code> and <code>target platform</code> variant dimensions have a defined meaning in Gradle, each project is free to define any number of flavors and apply meaning to them in any way.</p> </div> <div class="paragraph"> <p>An example of component flavors might differentiate between 'demo', 'paid' and 'enterprise' editions of the component, where the same set of sources is used to produce binaries with different functions.</p> </div> </div> <div class="sect2"> <h3 id="example_defining_flavors"><a class="anchor" href="#example_defining_flavors"></a><a class="link" href="#example_defining_flavors">Example: Defining flavors</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { flavors { english french } components { hello(NativeLibrarySpec) { binaries.all { if (flavor == flavors.french) { cppCompiler.define "FRENCH" } } } } }</code></pre> </div> </div> <div class="paragraph"> <p>In the example above, a library is defined with a 'english' and 'french' flavor. When compiling the 'french' variant, a separate macro is defined which leads to a different binary being produced.</p> </div> <div class="paragraph"> <p>If no flavor is defined for a component, then a single default flavor named 'default' is used.</p> </div> </div> <div class="sect2"> <h3 id="sec:selecting_the_build_types_platforms_and_flavors_for_a_component"><a class="anchor" href="#sec:selecting_the_build_types_platforms_and_flavors_for_a_component"></a><a class="link" href="#sec:selecting_the_build_types_platforms_and_flavors_for_a_component">Selecting the build types, platforms and flavors for a component</a></h3> <div class="paragraph"> <p>For a default component, Gradle will attempt to create a native binary variant for each and every combination of <code>buildType</code> and <code>flavor</code> defined for the project. It is possible to override this on a per-component basis, by specifying the set of <code>targetBuildTypes</code> and/or <code>targetFlavors</code>. By default, Gradle will build for the default platform, see <a href="#native_binaries:platform">above</a>, unless specified explicitly on a per-component basis by specifying a set of <code>targetPlatforms</code>.</p> </div> </div> <div class="sect2"> <h3 id="example_targeting_a_component_at_particular_platforms"><a class="anchor" href="#example_targeting_a_component_at_particular_platforms"></a><a class="link" href="#example_targeting_a_component_at_particular_platforms">Example: Targeting a component at particular platforms</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { components { hello(NativeLibrarySpec) { targetPlatform "x86" targetPlatform "x64" } main(NativeExecutableSpec) { targetPlatform "x86" targetPlatform "x64" sources { cpp.lib library: 'hello', linkage: 'static' } } } }</code></pre> </div> </div> <div class="paragraph"> <p>Here you can see that the <a href="../dsl/org.gradle.nativeplatform.TargetedNativeComponent.html#org.gradle.nativeplatform.TargetedNativeComponent:targetPlatform(java.lang.String)">TargetedNativeComponent.targetPlatform(java.lang.String)</a> method is used to specify a platform that the <code>NativeExecutableSpec</code> named <code>main</code> should be built for.</p> </div> <div class="paragraph"> <p>A similar mechanism exists for selecting <a href="../dsl/org.gradle.nativeplatform.TargetedNativeComponent.html#org.gradle.nativeplatform.TargetedNativeComponent:targetBuildTypes(java.lang.String[])">TargetedNativeComponent.targetBuildTypes(java.lang.String&#8230;&#8203;)</a> and <a href="../dsl/org.gradle.nativeplatform.TargetedNativeComponent.html#org.gradle.nativeplatform.TargetedNativeComponent:targetFlavors(java.lang.String[])">TargetedNativeComponent.targetFlavors(java.lang.String&#8230;&#8203;)</a>.</p> </div> </div> <div class="sect2"> <h3 id="sec:building_all_possible_variants"><a class="anchor" href="#sec:building_all_possible_variants"></a><a class="link" href="#sec:building_all_possible_variants">Building all possible variants</a></h3> <div class="paragraph"> <p>When a set of build types, target platforms, and flavors is defined for a component, a <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> model element is created for every possible combination of these. However, in many cases it is not possible to build a particular variant, perhaps because no tool chain is available to build for a particular platform.</p> </div> <div class="paragraph"> <p>If a binary variant cannot be built for any reason, then the <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> associated with that variant will not be <code>buildable</code>. It is possible to use this property to create a task to generate all possible variants on a particular machine.</p> </div> </div> <div class="sect2"> <h3 id="example_building_all_possible_variants"><a class="anchor" href="#example_building_all_possible_variants"></a><a class="link" href="#example_building_all_possible_variants">Example: Building all possible variants</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { tasks { buildAllExecutables(Task) { dependsOn $.binaries.findAll { it.buildable } } } }</code></pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:tool_chain"><a class="anchor" href="#native_binaries:tool_chain"></a><a class="link" href="#native_binaries:tool_chain">Tool chains</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>A single build may utilize different tool chains to build variants for different platforms. To this end, the core 'native-binary' plugins will attempt to locate and make available supported tool chains. However, the set of tool chains for a project may also be explicitly defined, allowing additional cross-compilers to be configured as well as allowing the install directories to be specified.</p> </div> <div class="sect2"> <h3 id="sec:defining_tool_chains"><a class="anchor" href="#sec:defining_tool_chains"></a><a class="link" href="#sec:defining_tool_chains">Defining tool chains</a></h3> <div class="paragraph"> <p>The supported tool chain types are:</p> </div> <div class="ulist"> <ul> <li> <p><a href="../dsl/org.gradle.nativeplatform.toolchain.Gcc.html">Gcc</a></p> </li> <li> <p><a href="../dsl/org.gradle.nativeplatform.toolchain.Clang.html">Clang</a></p> </li> <li> <p><a href="../dsl/org.gradle.nativeplatform.toolchain.VisualCpp.html">VisualCpp</a></p> </li> </ul> </div> </div> <div class="sect2"> <h3 id="example_defining_tool_chains"><a class="anchor" href="#example_defining_tool_chains"></a><a class="link" href="#example_defining_tool_chains">Example: Defining tool chains</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { toolChains { visualCpp(VisualCpp) { // Specify the installDir if Visual Studio cannot be located // installDir "C:/Apps/Microsoft Visual Studio 10.0" } gcc(Gcc) { // Uncomment to use a GCC install that is not in the PATH // path "/usr/bin/gcc" } clang(Clang) } }</code></pre> </div> </div> <div class="paragraph"> <p>Each tool chain implementation allows for a certain degree of configuration (see the API documentation for more details).</p> </div> </div> <div class="sect2"> <h3 id="sec:using_tool_chains"><a class="anchor" href="#sec:using_tool_chains"></a><a class="link" href="#sec:using_tool_chains">Using tool chains</a></h3> <div class="paragraph"> <p>It is not necessary or possible to specify the tool chain that should be used to build. For a given variant, Gradle will attempt to locate a <a href="../javadoc/org/gradle/nativeplatform/toolchain/NativeToolChain.html">NativeToolChain</a> that is able to build for the target platform. Available tool chains are searched in the order defined.</p> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> When a platform does not define an architecture or operating system, the default target of the tool chain is assumed. So if a platform does not define a value for <code>operatingSystem</code>, Gradle will find the first available tool chain that can build for the specified <code>architecture</code>. </td> </tr> </table> </div> <div class="paragraph"> <p>The core Gradle tool chains are able to target the following architectures out of the box. In each case, the tool chain will target the current operating system. See the next section for information on cross-compiling for other operating systems.</p> </div> <table class="tableblock frame-all grid-all stretch"> <colgroup> <col style="width: 50%;"> <col style="width: 50%;"> </colgroup> <thead> <tr> <th class="tableblock halign-left valign-top">Tool Chain</th> <th class="tableblock halign-left valign-top">Architectures</th> </tr> </thead> <tbody> <tr> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>GCC</p> </div></div></td> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>x86, x86_64, arm64 (macOS &amp; linux Only)</p> </div></div></td> </tr> <tr> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>Clang</p> </div></div></td> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>x86, x86_64, arm64 (macOS &amp; linux only)</p> </div></div></td> </tr> <tr> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>Visual C++</p> </div></div></td> <td class="tableblock halign-left valign-top"><div class="content"><div class="paragraph"> <p>x86, x86_64, ia-64</p> </div></div></td> </tr> </tbody> </table> <div class="paragraph"> <p>So for GCC running on linux, the supported target platforms are 'linux/x86' and 'linux/x86_64'. For GCC running on Windows via Cygwin, platforms 'windows/x86' and 'windows/x86_64' are supported. (The Cygwin POSIX runtime is not yet modelled as part of the platform, but will be in the future.)</p> </div> <div class="paragraph"> <p>If no target platforms are defined for a project, then all binaries are built to target a default platform named 'current'. This default platform does not specify any <code>architecture</code> or <code>operatingSystem</code> value, hence using the default values of the first available tool chain.</p> </div> <div class="paragraph"> <p>Gradle provides a <em>hook</em> that allows the build author to control the exact set of arguments passed to a tool chain executable. This enables the build author to work around any limitations in Gradle, or assumptions that Gradle makes. The arguments hook should be seen as a 'last-resort' mechanism, with preference given to truly modelling the underlying domain.</p> </div> </div> <div class="sect2"> <h3 id="example_reconfigure_tool_arguments"><a class="anchor" href="#example_reconfigure_tool_arguments"></a><a class="link" href="#example_reconfigure_tool_arguments">Example: Reconfigure tool arguments</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { toolChains { visualCpp(VisualCpp) { eachPlatform { cppCompiler.withArguments { args -&gt; args &lt;&lt; "-DFRENCH" } } } clang(Clang) { eachPlatform { cCompiler.withArguments { args -&gt; Collections.replaceAll(args, "CUSTOM", "-DFRENCH") } linker.withArguments { args -&gt; args.remove "CUSTOM" } staticLibArchiver.withArguments { args -&gt; args.remove "CUSTOM" } } } } }</code></pre> </div> </div> </div> <div class="sect2"> <h3 id="sec:crosscompiling_with_gcc"><a class="anchor" href="#sec:crosscompiling_with_gcc"></a><a class="link" href="#sec:crosscompiling_with_gcc">Cross-compiling with GCC</a></h3> <div class="paragraph"> <p>Cross-compiling is possible with the <a href="../dsl/org.gradle.nativeplatform.toolchain.Gcc.html">Gcc</a> and <a href="../dsl/org.gradle.nativeplatform.toolchain.Clang.html">Clang</a> tool chains, by adding support for additional target platforms. This is done by specifying a target platform for a toolchain. For each target platform a custom configuration can be specified.</p> </div> </div> <div class="sect2"> <h3 id="example_defining_target_platforms"><a class="anchor" href="#example_defining_target_platforms"></a><a class="link" href="#example_defining_target_platforms">Example: Defining target platforms</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { toolChains { gcc(Gcc) { target("arm"){ cppCompiler.withArguments { args -&gt; args &lt;&lt; "-m32" } linker.withArguments { args -&gt; args &lt;&lt; "-m32" } } target("sparc") } } platforms { arm { architecture "arm" } sparc { architecture "sparc" } } components { main(NativeExecutableSpec) { targetPlatform "arm" targetPlatform "sparc" } } }</code></pre> </div> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:visual_studio"><a class="anchor" href="#native_binaries:visual_studio"></a><a class="link" href="#native_binaries:visual_studio">Visual Studio IDE integration</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>Gradle has the ability to generate Visual Studio project and solution files for the native components defined in your build. This ability is added by the <code>visual-studio</code> plugin. For a multi-project build, all projects with native components (and the root project) should have this plugin applied.</p> </div> <div class="paragraph"> <p>When the <code>visual-studio</code> plugin is applied to the root project, a task named <code>visualStudio</code> is created, which will generate a Visual Studio solution file containing all components in the build. This solution will include a Visual Studio project for each component, as well as configuring each component to build using Gradle.</p> </div> <div class="paragraph"> <p>A task named <code>openVisualStudio</code> is also created by the <code>visual-studio</code> plugin when the project is the root project. This task generates the Visual Studio solution and then opens the solution in Visual Studio. This means you can simply run <code>gradlew openVisualStudio</code> from the root project to generate and open the Visual Studio solution in one convenient step.</p> </div> <div class="paragraph"> <p>The content of the generated visual studio files can be modified via API hooks, provided by the <code>visualStudio</code> extension. Take a look at the 'visual-studio' sample, or see <a href="../dsl/org.gradle.ide.visualstudio.VisualStudioExtension.html#org.gradle.ide.visualstudio.VisualStudioExtension:projects">VisualStudioExtension.getProjects()</a> and <a href="../dsl/org.gradle.ide.visualstudio.VisualStudioRootExtension.html#org.gradle.ide.visualstudio.VisualStudioRootExtension:solution">VisualStudioRootExtension.getSolution()</a> in the API documentation for more details.</p> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:cunit"><a class="anchor" href="#native_binaries:cunit"></a><a class="link" href="#native_binaries:cunit">CUnit support</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>The Gradle <code>cunit</code> plugin provides support for compiling and executing CUnit tests in your native-binary project. For each <a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a> and <a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a> defined in your project, Gradle will create a matching <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteSpec.html">CUnitTestSuiteSpec</a> component, named <code>${component.name}Test</code>.</p> </div> <div class="sect2"> <h3 id="sec:cunit_sources"><a class="anchor" href="#sec:cunit_sources"></a><a class="link" href="#sec:cunit_sources">CUnit sources</a></h3> <div class="paragraph"> <p>Gradle will create a <a href="../dsl/org.gradle.language.c.CSourceSet.html">CSourceSet</a> named 'cunit' for each <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteSpec.html">CUnitTestSuiteSpec</a> component in the project. This source set should contain the cunit test files for the component under test. Source files can be located in the conventional location (<code>src/${component.name}Test/cunit</code>) or can be configured like any other source set.</p> </div> <div class="paragraph"> <p>Gradle initialises the CUnit test registry and executes the tests, utilising some generated CUnit launcher sources. Gradle will expect and call a function with the signature <code>void gradle_cunit_register()</code> that you can use to configure the actual CUnit suites and tests to execute.</p> </div> </div> <div class="sect2"> <h3 id="example_registering_cunit_tests"><a class="anchor" href="#example_registering_cunit_tests"></a><a class="link" href="#example_registering_cunit_tests">Example: Registering CUnit tests</a></h3> <div class="listingblock multi-language-sample"> <div class="title">suite_operators.c</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="c">#include &lt;CUnit/Basic.h&gt; #include "gradle_cunit_register.h" #include "test_operators.h" int suite_init(void) { return 0; } int suite_clean(void) { return 0; } void gradle_cunit_register() { CU_pSuite pSuiteMath = CU_add_suite("operator tests", suite_init, suite_clean); CU_add_test(pSuiteMath, "test_plus", test_plus); CU_add_test(pSuiteMath, "test_minus", test_minus); }</code></pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> Due to this mechanism, your CUnit sources may not contain a <code>main</code> method since this will clash with the method provided by Gradle. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="sec:building_cunit_executables"><a class="anchor" href="#sec:building_cunit_executables"></a><a class="link" href="#sec:building_cunit_executables">Building CUnit executables</a></h3> <div class="paragraph"> <p>A <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteSpec.html">CUnitTestSuiteSpec</a> component has an associated <a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a> or <a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a> component. For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> configured for the main component, a matching <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteBinarySpec.html">CUnitTestSuiteBinarySpec</a> will be configured on the test suite component. These test suite binaries can be configured in a similar way to any other binary instance:</p> </div> </div> <div class="sect2"> <h3 id="example_configuring_cunit_tests"><a class="anchor" href="#example_configuring_cunit_tests"></a><a class="link" href="#example_configuring_cunit_tests">Example: Configuring CUnit tests</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { binaries { withType(CUnitTestSuiteBinarySpec) { lib library: "cunit", linkage: "static" if (flavor == flavors.failing) { cCompiler.define "PLUS_BROKEN" } } } }</code></pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> Both the CUnit sources provided by your project and the generated launcher require the core CUnit headers and libraries. Presently, this library dependency must be provided by your project for each <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteBinarySpec.html">CUnitTestSuiteBinarySpec</a>. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="sec:running_cunit_tests"><a class="anchor" href="#sec:running_cunit_tests"></a><a class="link" href="#sec:running_cunit_tests">Running CUnit tests</a></h3> <div class="paragraph"> <p>For each <a href="../dsl/org.gradle.nativeplatform.test.cunit.CUnitTestSuiteBinarySpec.html">CUnitTestSuiteBinarySpec</a>, Gradle will create a task to execute this binary, which will run all of the registered CUnit tests. Test results will be found in the <code><em>${build.dir}</em>/test-results</code> directory.</p> </div> </div> <div class="sect2"> <h3 id="example_running_cunit_tests"><a class="anchor" href="#example_running_cunit_tests"></a><a class="link" href="#example_running_cunit_tests">Example: Running CUnit tests</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">plugins { id 'c' id 'cunit-test-suite' } model { flavors { passing failing } platforms { x86 { if (operatingSystem.macOsX) { architecture "x64" } else { architecture "x86" } } } repositories { libs(PrebuiltLibraries) { cunit { headers.srcDir "libs/cunit/2.1-2/include" binaries.withType(StaticLibraryBinary) { staticLibraryFile = file("libs/cunit/2.1-2/lib/" + findCUnitLibForPlatform(targetPlatform)) } } } } components { operators(NativeLibrarySpec) { targetPlatform "x86" } } testSuites { operatorsTest(CUnitTestSuiteSpec) { testing $.components.operators } } } model { binaries { withType(CUnitTestSuiteBinarySpec) { lib library: "cunit", linkage: "static" if (flavor == flavors.failing) { cCompiler.define "PLUS_BROKEN" } } } }</code></pre> </div> </div> <div class="listingblock"> <div class="title">Output of <code>gradle -q runOperatorsTestFailingCUnitExe</code></div> <div class="content"> <pre>&gt; gradle -q runOperatorsTestFailingCUnitExe There were test failures: 1. /home/user/gradle/samples/src/operatorsTest/c/test_plus.c:6 - plus(0, -2) == -2 2. /home/user/gradle/samples/src/operatorsTest/c/test_plus.c:7 - plus(2, 2) == 4 FAILURE: Build failed with an exception. * What went wrong: Execution failed for task ':runOperatorsTestFailingCUnitExe'. &gt; There were failing tests. See the results at: file:///home/user/gradle/samples/build/test-results/operatorsTest/failing/ * Try: &gt; Run with --stacktrace option to get the stack trace. &gt; Run with --info or --debug option to get more log output. &gt; Run with --scan to get full insights. &gt; Get more help at https://help.gradle.org. BUILD FAILED in 0s</pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> <div class="paragraph"> <p>The current support for CUnit is quite rudimentary. Plans for future integration include:</p> </div> <div class="ulist"> <ul> <li> <p>Allow tests to be declared with Javadoc-style annotations.</p> </li> <li> <p>Improved HTML reporting, similar to that available for JUnit.</p> </li> <li> <p>Real-time feedback for test execution.</p> </li> <li> <p>Support for additional test frameworks.</p> </li> </ul> </div> </td> </tr> </table> </div> </div> </div> </div> <div class="sect1"> <h2 id="native_binaries:google_test"><a class="anchor" href="#native_binaries:google_test"></a><a class="link" href="#native_binaries:google_test">GoogleTest support</a></h2> <div class="sectionbody"> <div class="paragraph"> <p>The Gradle <code>google-test</code> plugin provides support for compiling and executing GoogleTest tests in your native-binary project. For each <a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a> and <a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a> defined in your project, Gradle will create a matching <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteSpec.html">GoogleTestTestSuiteSpec</a> component, named <code>${component.name}Test</code>.</p> </div> <div class="sect2"> <h3 id="sec:googletest_sources"><a class="anchor" href="#sec:googletest_sources"></a><a class="link" href="#sec:googletest_sources">GoogleTest sources</a></h3> <div class="paragraph"> <p>Gradle will create a <a href="../dsl/org.gradle.language.cpp.CppSourceSet.html">CppSourceSet</a> named 'cpp' for each <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteSpec.html">GoogleTestTestSuiteSpec</a> component in the project. This source set should contain the GoogleTest test files for the component under test. Source files can be located in the conventional location (<code>src/${component.name}Test/cpp</code>) or can be configured like any other source set.</p> </div> </div> <div class="sect2"> <h3 id="sec:building_googletest_executables"><a class="anchor" href="#sec:building_googletest_executables"></a><a class="link" href="#sec:building_googletest_executables">Building GoogleTest executables</a></h3> <div class="paragraph"> <p>A <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteSpec.html">GoogleTestTestSuiteSpec</a> component has an associated <a href="../javadoc/org/gradle/nativeplatform/NativeExecutableSpec.html">NativeExecutableSpec</a> or <a href="../javadoc/org/gradle/nativeplatform/NativeLibrarySpec.html">NativeLibrarySpec</a> component. For each <a href="../javadoc/org/gradle/nativeplatform/NativeBinarySpec.html">NativeBinarySpec</a> configured for the main component, a matching <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteBinarySpec.html">GoogleTestTestSuiteBinarySpec</a> will be configured on the test suite component. These test suite binaries can be configured in a similar way to any other binary instance:</p> </div> </div> <div class="sect2"> <h3 id="example_registering_googletest_tests"><a class="anchor" href="#example_registering_googletest_tests"></a><a class="link" href="#example_registering_googletest_tests">Example: Registering GoogleTest tests</a></h3> <div class="listingblock multi-language-sample"> <div class="title">build.gradle</div> <div class="content"> <pre class="prettyprint highlight"><code data-lang="groovy">model { binaries { withType(GoogleTestTestSuiteBinarySpec) { lib library: "googleTest", linkage: "static" if (flavor == flavors.failing) { cppCompiler.define "PLUS_BROKEN" } if (targetPlatform.operatingSystem.linux) { cppCompiler.args '-pthread' linker.args '-pthread' if (toolChain instanceof Gcc || toolChain instanceof Clang) { // Use C++03 with the old ABIs, as this is what the googletest binaries were built with cppCompiler.args '-std=c++03', '-D_GLIBCXX_USE_CXX11_ABI=0' linker.args '-std=c++03' } } } } }</code></pre> </div> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> The GoogleTest sources provided by your project require the core GoogleTest headers and libraries. Presently, this library dependency must be provided by your project for each <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteBinarySpec.html">GoogleTestTestSuiteBinarySpec</a>. </td> </tr> </table> </div> </div> <div class="sect2"> <h3 id="sec:running_googletest_tests"><a class="anchor" href="#sec:running_googletest_tests"></a><a class="link" href="#sec:running_googletest_tests">Running GoogleTest tests</a></h3> <div class="paragraph"> <p>For each <a href="../dsl/org.gradle.nativeplatform.test.googletest.GoogleTestTestSuiteBinarySpec.html">GoogleTestTestSuiteBinarySpec</a>, Gradle will create a task to execute this binary, which will run all of the registered GoogleTest tests. Test results will be found in the <code><em>${build.dir}</em>/test-results</code> directory.</p> </div> <div class="admonitionblock note"> <table> <tr> <td class="icon"> <i class="fa icon-note" title="Note"></i> </td> <td class="content"> <div class="paragraph"> <p>The current support for GoogleTest is quite rudimentary. Plans for future integration include:</p> </div> <div class="ulist"> <ul> <li> <p>Improved HTML reporting, similar to that available for JUnit.</p> </li> <li> <p>Real-time feedback for test execution.</p> </li> <li> <p>Support for additional test frameworks.</p> </li> </ul> </div> </td> </tr> </table> </div> </div> </div> </div> </div> <div id="feedback-container" class="feedback-container"> <div class="feedback-buttons"> <label id="feedback-container-label"> Was this page helpful?</label> <button id="thumbs-up" onclick="showFeedbackForm(true)"> <!-- Thumbs Up SVG --> <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="24px" height="24px" viewBox="0 0 24 24" version="1.1"> <g id="surface1"> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 3 21.375 C 3 21.582031 2.832031 21.75 2.625 21.75 C 2.417969 21.75 2.25 21.582031 2.25 21.375 C 2.25 21.167969 2.417969 21 2.625 21 C 2.832031 21 3 21.167969 3 21.375 Z M 3 21.375 "/> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 5.25 9.75 C 5.25 8.921875 4.578125 8.25 3.75 8.25 L 1.5 8.25 C 0.671875 8.25 0 8.921875 0 9.75 L 0 22.5 C 0 23.328125 0.671875 24 1.5 24 L 3.75 24 C 4.578125 24 5.25 23.328125 5.25 22.5 Z M 2.625 22.5 C 2.003906 22.5 1.5 21.996094 1.5 21.375 C 1.5 20.753906 2.003906 20.25 2.625 20.25 C 3.246094 20.25 3.75 20.753906 3.75 21.375 C 3.75 21.996094 3.246094 22.5 2.625 22.5 Z M 2.625 22.5 "/> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 24 10.5 C 24 9.257812 22.992188 8.25 21.75 8.25 L 15.367188 8.25 L 15.375 8.25 L 16.125 1.5 C 16.203125 0.679688 15.640625 0 14.8125 0 L 13.3125 0 C 12.375 0 11.984375 0.65625 11.625 1.5 L 8.625 8.25 C 7.816406 10.1875 6.75 10.5 6 10.5 L 6 21.832031 C 6.449219 21.9375 7.019531 22.1875 7.578125 22.761719 C 8.746094 23.960938 10.140625 24 10.875 24 L 19.5 24 C 20.742188 24 21.75 22.992188 21.75 21.75 C 21.75 21.101562 21.472656 20.515625 21.035156 20.105469 C 21.890625 19.789062 22.5 18.964844 22.5 18 C 22.5 17.351562 22.222656 16.765625 21.785156 16.355469 C 22.640625 16.039062 23.25 15.214844 23.25 14.25 C 23.25 13.601562 22.972656 13.015625 22.535156 12.605469 C 23.390625 12.289062 24 11.464844 24 10.5 Z M 24 10.5 "/> </g> </svg> </button> <button id="thumbs-down" onclick="showFeedbackForm(false)"> <!-- Thumbs Down SVG --> <svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="24px" height="24px" viewBox="0 0 24 24" version="1.1"> <g id="surface1"> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 3 13.125 C 3 13.332031 2.832031 13.5 2.625 13.5 C 2.417969 13.5 2.25 13.332031 2.25 13.125 C 2.25 12.917969 2.417969 12.75 2.625 12.75 C 2.832031 12.75 3 12.917969 3 13.125 Z M 3 13.125 "/> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 0 1.5 C 0 0.671875 0.671875 0 1.5 0 L 3.75 0 C 4.578125 0 5.25 0.671875 5.25 1.5 L 5.25 14.25 C 5.25 15.078125 4.578125 15.75 3.75 15.75 L 1.5 15.75 C 0.671875 15.75 0 15.078125 0 14.25 Z M 2.625 14.25 C 3.246094 14.25 3.75 13.746094 3.75 13.125 C 3.75 12.503906 3.246094 12 2.625 12 C 2.003906 12 1.5 12.503906 1.5 13.125 C 1.5 13.746094 2.003906 14.25 2.625 14.25 Z M 2.625 14.25 "/> <path style=" stroke:none;fill-rule:nonzero;fill:rgb(10.588235%,65.882353%,79.607843%);fill-opacity:1;" d="M 24 13.5 C 24 14.742188 22.992188 15.75 21.75 15.75 L 15.367188 15.75 L 15.375 15.75 L 16.125 22.5 C 16.203125 23.320312 15.640625 24 14.8125 24 L 13.3125 24 C 12.375 24 11.984375 23.34375 11.625 22.5 L 8.625 15.75 C 7.816406 13.8125 6.75 13.5 6 13.5 L 6 2.167969 C 6.449219 2.0625 7.019531 1.8125 7.578125 1.238281 C 8.746094 0.0390625 10.140625 0 10.875 0 L 19.5 0 C 20.742188 0 21.75 1.007812 21.75 2.25 C 21.75 2.898438 21.472656 3.484375 21.035156 3.894531 C 21.890625 4.210938 22.5 5.035156 22.5 6 C 22.5 6.648438 22.222656 7.234375 21.785156 7.644531 C 22.640625 7.960938 23.25 8.785156 23.25 9.75 C 23.25 10.398438 22.972656 10.984375 22.535156 11.394531 C 23.390625 11.710938 24 12.535156 24 13.5 Z M 24 13.5 "/> </g> </svg> </button> </div> <div id="feedback-form" class="hidden-feedback-form"> <form> <label for="feedback">Additional Feedback:</label> <textarea id="feedback-text" name="feedback-text" rows="4" cols="50" placeholder="Tell us more about your experience."></textarea> <div>You can <a href="https://github.com/gradle/gradle/issues/new?assignees=&labels=a%3Adocumentation%2Cto-triage&projects=&template=40_contributor_documentation.yml"> submit issues</a> directly on Github.</div> <button id="feedback-button" type="button" onclick="submitAdditionalFeedback()" disabled> Submit Feedback <div class="animate-flicker"></div> </button> </form> </div> </div><script src="https://cdnjs.cloudflare.com/ajax/libs/prettify/r298/run_prettify.min.js"></script> </div> <!-- end div class="chapter" --> <div id="analytics-consent-div"></div><footer class="site-layout__footer site-footer" itemscope="itemscope" itemtype="https://schema.org/WPFooter"> <nav class="site-footer__navigation" itemtype="https://schema.org/SiteNavigationElement"> <section class="site-footer__links"> <div class="site-footer__link-group"> <header><strong>Docs</strong></header> <ul class="site-footer__links-list"> <li itemprop="name"><a href="/release-notes.html" itemprop="url">Release Notes</a></li> <li itemprop="name"><a href="/dsl/" itemprop="url">Groovy DSL</a></li> <li itemprop="name"><a href="/kotlin-dsl/" itemprop="url">Kotlin DSL</a></li> <li itemprop="name"><a href="/javadoc/" itemprop="url">Javadoc</a></li> </ul> </div> <div class="site-footer__link-group"> <header><strong>News</strong></header> <ul class="site-footer__links-list"> <li itemprop="name"><a href="https://blog.gradle.org/" itemprop="url">Blog</a></li> <li itemprop="name"><a href="https://newsletter.gradle.org/" itemprop="url">Newsletter</a></li> <li itemprop="name"><a href="https://twitter.com/gradle" itemprop="url">Twitter</a></li> <li itemprop="name"><a href="https://status.gradle.com/" itemprop="url">Status</a></li> </ul> </div> <div class="site-footer__link-group"> <header><strong>Products</strong></header> <ul class="site-footer__links-list"> <li itemprop="name"><a href="https://gradle.com/develocity/" itemprop="url">Develocity</a></li> <li itemprop="name"><a href="https://gradle.com/build-scans/" itemprop="url">Build Scan™</a></li> <li itemprop="name"><a href="https://gradle.com/build-cache/" itemprop="url">Build Cache</a></li> <li itemprop="name"><a href="https://gradle.org/services/" itemprop="url">Services</a></li> </ul> </div> <div class="site-footer__link-group"> <header><strong>Get Help</strong></header> <ul class="site-footer__links-list"> <li itemprop="name"><a href="https://discuss.gradle.org/c/help-discuss" itemprop="url">Forums</a></li> <li itemprop="name"><a href="https://github.com/gradle/" itemprop="url">GitHub</a></li> <li itemprop="name"><a href="https://gradle.org/training/" itemprop="url">Events</a></li> <li itemprop="name"><a href="https://dpeuniversity.gradle.com/" itemprop="url">DPE University</a></li> </ul> </div> </section> <section class="site-footer__subscribe-newsletter" id="newsletter-form-container"> <header class="newsletter-form__header"><h5>Stay <code>UP-TO-DATE</code> on new features and news</h5></header> <p class="disclaimer">By entering your email, you agree to our <a href="https://gradle.com/legal/terms-of-service/">Terms</a> and <a href="https://gradle.com/legal/privacy/">Privacy Policy</a>, including receipt of emails. You can unsubscribe at any time.</p> <div class="newsletter-form__container"> <form id="newsletter-form" class="newsletter-form" action="https://go.gradle.com/l/68052/2018-09-07/bk6wml" method="post"> <input id="email" class="email" name="email" type="email" placeholder="name@email.com" pattern="[^@\s]+@[^@\s]+\.[^@\s]+" maxlength="255" required=""/> <button id="submit" class="submit" type="submit">Subscribe</button> </form> </div> </section> </nav> </footer> </div> <!-- end div class="content" --> </main> <div class="site-footer-secondary"> <div class="site-footer-secondary__contents"> <div class="site-footer__copy">© <a href="https://gradle.com">Gradle Inc.</a> <time>2023</time> All rights reserved. </div> <div class="site-footer__logo"><a href="/"> <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 90 66.06"> <title>Gradle</title> <path class="cls-1" d="M85.11,4.18a14.27,14.27,0,0,0-19.83-.34,1.38,1.38,0,0,0,0,2L67,7.6a1.36,1.36,0,0,0,1.78.12A8.18,8.18,0,0,1,79.5,20.06C68.17,31.38,53.05-.36,18.73,16a4.65,4.65,0,0,0-2,6.54l5.89,10.17a4.64,4.64,0,0,0,6.3,1.73l.14-.08-.11.08L31.53,33a60.29,60.29,0,0,0,8.22-6.13,1.44,1.44,0,0,1,1.87-.06h0a1.34,1.34,0,0,1,.06,2A61.61,61.61,0,0,1,33,35.34l-.09,0-2.61,1.46a7.34,7.34,0,0,1-3.61.94,7.45,7.45,0,0,1-6.47-3.71l-5.57-9.61C4,32-2.54,46.56,1,65a1.36,1.36,0,0,0,1.33,1.11H8.61A1.36,1.36,0,0,0,10,64.87a9.29,9.29,0,0,1,18.42,0,1.35,1.35,0,0,0,1.34,1.19H35.9a1.36,1.36,0,0,0,1.34-1.19,9.29,9.29,0,0,1,18.42,0A1.36,1.36,0,0,0,57,66.06H63.1a1.36,1.36,0,0,0,1.36-1.34c.14-8.6,2.46-18.48,9.07-23.43C96.43,24.16,90.41,9.48,85.11,4.18ZM61.76,30.05l-4.37-2.19h0a2.74,2.74,0,1,1,4.37,2.2Z"/> </svg> </a></div> <div class="site-footer-secondary__links"> <a href="https://gradle.com/careers/">Careers</a> | <a href="https://gradle.com/legal/privacy/">Privacy</a> | <a href="https://gradle.com/legal/terms-of-service/">Terms of Service</a> | <a href="https://gradle.org/contact/">Contact</a> </div> </div> </div> </div> <!-- end div class="layout" --> <script type="text/javascript"> // Polyfill Element.matches() if (!Element.prototype.matches) { Element.prototype.matches = Element.prototype.msMatchesSelector || Element.prototype.webkitMatchesSelector; } // Polyfill Element.closest() if (!Element.prototype.closest) { Element.prototype.closest = function (s) { var el = this; if (!document.documentElement.contains(el)) return null; do { if (typeof el.matches === "function" && el.matches(s)) return el; el = el.parentElement || el.parentNode; } while (el !== null); return null; }; } function getCurrentChapterFileName(givenUrl) { var currentChapterFileName = givenUrl.substr(givenUrl.lastIndexOf("/") + 1); if (currentChapterFileName === "index.html" || currentChapterFileName === "") { currentChapterFileName = givenUrl.substr(0, givenUrl.lastIndexOf("/")); currentChapterFileName = currentChapterFileName.substr(currentChapterFileName.lastIndexOf("/") + 1) + "/index.html"; } return currentChapterFileName; } // The media query indicating that a device is a desktop. // The `min-width: 64rem` definition should be aligned to // the one of `css/manual.css`. const desktopMediaQuery = window.matchMedia("screen and (min-width: 64rem)"); [].forEach.call(document.querySelectorAll(".docs-navigation a[href$='/" + getCurrentChapterFileName(window.location.pathname) + "']"), function (link) { // Add "active" to all links same as current URL link.classList.add("active"); // Expand all parent navigation var parentListEl = link.closest("li"); while (parentListEl !== null) { var dropDownEl = parentListEl.querySelector(".nav-dropdown"); if (dropDownEl !== null) { dropDownEl.classList.add("expanded"); } parentListEl = parentListEl.parentNode.closest("li"); } // Only scroll if the device is a desktop. // // Mobile's `docs-navigation` is always at bottom of `content`, // so we should not slide down to where `docs-navigation` lays. if (desktopMediaQuery.matches) { // Scroll to center of the page link.scrollIntoView({behavior: 'auto', block: 'center', inline: 'center'}) } }); // Expand/contract multi-level side navigation [].forEach.call(document.querySelectorAll(".docs-navigation .nav-dropdown"), function registerSideNavActions(collapsibleElement) { collapsibleElement.addEventListener("click", function toggleExpandedSideNav(evt) { evt.preventDefault(); evt.target.classList.toggle("expanded"); evt.target.setAttribute("aria-expanded", evt.target.classList.contains("expanded").toString()); return false; }, false); }); // Fix a weird issue making the initial screen always at the bottom. document.querySelector(".content").scrollIntoView(true); </script> </body> </html>

Pages: 1 2 3 4 5 6 7 8 9 10