From: Ladislav Michl <[email protected]>

Let PTXdist offer to create the project from template when BSP
directory it is running from appears unconfigured.

Nothing is written before all questions are answered, so declining or
Ctrl-C leaves the directory untouched.

Without a terminal or for configs given with --ptxconfig/--platformconfig,
the error is shown as before. The toolchain check is disabled in the new
platformconfig, as there is no toolchain yet.

The host tools prepared in ~/.cache before the project existed are
copied into it, so they are not built twice.

Signed-off-by: Ladislav Michl <[email protected]>
---
 README                                 |   3 +
 bin/ptxdist                            | 146 ++++++++++++++++++++++++-
 doc/ref_parameter.rst                  |   4 +
 rules/templates/project/gitignore      |   9 ++
 rules/templates/project/platformconfig |  10 ++
 rules/templates/project/ptxconfig      |   6 +
 6 files changed, 174 insertions(+), 4 deletions(-)
 create mode 100644 rules/templates/project/gitignore
 create mode 100644 rules/templates/project/platformconfig
 create mode 100644 rules/templates/project/ptxconfig

diff --git a/README b/README
index 5774e046a..5ac1c6468 100644
--- a/README
+++ b/README
@@ -31,6 +31,9 @@ all missing tools at once, and builds kconfig in 
.ptxdist/<version>/
 (.ptxdist/git/ for git checkouts) inside the BSP. The PTXdist tree
 itself is never written to.
 
+In case the BSP directory appears uninitialized, PTXdist offers to
+create the project from template.
+
 Idea
 ----
 
diff --git a/bin/ptxdist b/bin/ptxdist
index 3c86aa225..65bc70ce8 100755
--- a/bin/ptxdist
+++ b/bin/ptxdist
@@ -264,11 +264,18 @@ check_version() {
 
 
 
+_init_hint() {
+       if [ -z "${ptxd_init_asked}" -a ! -t 0 ]; then
+               echo "  or run ptxdist in a terminal to create a new ${1}"
+       fi
+}
+
 _get_config_ptx() {
-       if [ ! -e "${PTXDIST_PTXCONFIG}" ]; then
+       if [ ! -e "${PTXDIST_PTXCONFIG}" ] && ! do_init ptx; then
                ptxd_dialog_msgbox \
                        "error: '${PTXDIST_PTXCONFIG#${PTXDIST_WORKSPACE}/}' 
file is missing\n" \
-                       "       try 'ptxdist select <ptxconfig>'\n"
+                       "       try 'ptxdist select <ptxconfig>'\n" \
+                       "$(_init_hint project)\n"
                return 1
        fi
 
@@ -321,10 +328,11 @@ _check_config_platform() {
        #
        ptxd_get_ptxconf PTXCONF_NO_PLATFORM >/dev/null && return || true
 
-       if [ ! -e "${PTXDIST_PLATFORMCONFIG}" ]; then
+       if [ ! -e "${PTXDIST_PLATFORMCONFIG}" ] && ! do_init platform; then
                ptxd_dialog_msgbox \
                        "error: 
'${PTXDIST_PLATFORMCONFIG#${PTXDIST_WORKSPACE}/}' is missing\n" \
-                       "       try 'ptxdist platform <platformconfig>'"
+                       "       try 'ptxdist platform <platformconfig>'\n" \
+                       "$(_init_hint platform)"
                return 1
        fi
 
@@ -1507,6 +1515,136 @@ do_select()
 }
 
 
+#
+# create what is missing for a new project on demand:
+# the ptxconfig and, if not selected either, the platformconfig,
+# or just the platformconfig; returns 1 if nothing was created.
+#
+# $1: what is missing: 'ptx' or 'platform'
+#
+do_init()
+{
+       local part="${1}"
+       local project platform arch answer
+       local -a archs
+       local templates="${PTXDIST_TOPDIR}/rules/templates/project"
+       local ptxconfig="configs/ptxconfig"
+       local platformconfig
+
+       # only interactive and only for the default locations
+       if [ ! -t 0 -o ! -t 1 -o -n "${PTX_MENU}" ]; then
+               return 1
+       fi
+       if [ "${part}" = ptx -a "${PTX_ptxconfig_SET}" = true ]; then
+               return 1
+       fi
+       if [ "${PTX_platformconfig_SET}" = true ]; then
+               [ "${part}" = platform ] && return 1
+       elif [ ! -e "${PTXDIST_PLATFORMCONFIG}" ]; then
+               platformconfig=new
+       fi
+
+       if [ "${part}" = ptx -a -e "${ptxconfig}" ]; then
+               return 1
+       fi
+
+       ptxd_init_asked=true
+       echo
+       if [ "${part}" = ptx ]; then
+               echo "${PTXDIST_LOG_PROMPT}there is no PTXdist project in 
'${PTXDIST_WORKSPACE}'"
+               read -e -p "${PTXDIST_LOG_PROMPT}create a new one? [y/N] " 
answer || return 1
+       else
+               echo "${PTXDIST_LOG_PROMPT}no platform is selected"
+               read -e -p "${PTXDIST_LOG_PROMPT}create a new one? [y/N] " 
answer || return 1
+       fi
+       case "${answer}" in
+       y|Y|yes) ;;
+       *) return 1 ;;
+       esac
+       echo
+
+       if [ "${part}" = ptx ]; then
+               project="$(basename "${PTXDIST_WORKSPACE}")"
+               ptxd_template_read "project name" project "${project}" || 
return 1
+               if [ -z "${project}" ]; then
+                       ptxd_bailout "the project name must not be empty"
+               fi
+       fi
+       if [ -n "${platformconfig}" ]; then
+               # the architectures from the main choice in architecture.in
+               archs=( $(awk '/^choice/ { c++ } c == 1 && /^\tconfig ARCH_/ { 
print $2 } /^endchoice/ && c == 1 { exit }' \
+                       "${PTXDIST_TOPDIR}/platforms/architecture.in") ) &&
+               ptxd_template_read_options "architecture" arch 
"${archs[@]#ARCH_}" || return 1
+               platform="${arch,,}"
+               while :; do
+                       ptxd_template_read "platform name" platform 
"${platform}" || return 1
+                       
platformconfig="configs/platform-${platform}/platformconfig"
+                       if [ -z "${platform}" ]; then
+                               echo "${PTXDIST_LOG_PROMPT}the platform name 
must not be empty"
+                       elif [ -e "${platformconfig}" ]; then
+                               echo "${PTXDIST_LOG_PROMPT}'${platformconfig}' 
already exists"
+                       else
+                               break
+                       fi
+               done
+       fi
+
+       # create everything after all questions answered
+       echo
+       if [ -n "${project}" ]; then
+               echo "${PTXDIST_LOG_PROMPT}creating project '${project}'"
+               mkdir -p configs rules projectroot &&
+               if [ ! -e .gitignore ]; then
+                       ptxd_replace_magic "${templates}/gitignore" > .gitignore
+               fi &&
+               PROJECT="${project}" \
+                       ptxd_replace_magic "${templates}/ptxconfig" > 
"${ptxconfig}" &&
+               ln -sf "${ptxconfig}" "${PTXDIST_PTXCONFIG_DEFAULT}" || return
+               PTXDIST_PTXCONFIG="${PTXDIST_PTXCONFIG_DEFAULT}"
+       fi
+       if [ -n "${platform}" ]; then
+               echo "${PTXDIST_LOG_PROMPT}creating platform '${platform}' 
(${arch,,})"
+               mkdir -p "$(dirname "${platformconfig}")" &&
+               PLATFORM="${platform}" ARCH="ARCH_${arch}" \
+                       ptxd_replace_magic "${templates}/platformconfig" > 
"${platformconfig}" &&
+               ln -sf "${platformconfig}" "${PTXDIST_PLATFORMCONFIG_DEFAULT}" 
|| return
+               PTXDIST_PLATFORMCONFIG="${PTXDIST_PLATFORMCONFIG_DEFAULT}"
+       fi
+
+       # this is a project now, keep the host tools with it
+       case "${PTXDIST_HOSTTOOLS_DIR}" in
+       "${PTXDIST_TOPDIR}"|"${PTXDIST_WORKSPACE}/.ptxdist/"*)
+               ;;
+       *)
+               if [ ! -e ".ptxdist/${PTXDIST_HOSTTOOLS_DIR##*/}" ]; then
+                       mkdir -p .ptxdist &&
+                       cp -a "${PTXDIST_HOSTTOOLS_DIR}" ".ptxdist/" || return
+               fi
+               ;;
+       esac
+
+       unset PTXDIST_PLATFORMDIR
+       setup_platform &&
+       setup_path &&
+       setup_export || return
+
+       # fill in the defaults for everything else
+       if [ -n "${project}" ]; then
+               KCONFIG_ALLCONFIG="${PTXDIST_WORKSPACE}/${ptxconfig}" \
+                       do_config alldefconfig ptx > /dev/null || return
+       fi
+       if [ -n "${platform}" ]; then
+               KCONFIG_ALLCONFIG="${PTXDIST_WORKSPACE}/${platformconfig}" \
+                       do_config alldefconfig platform > /dev/null || return
+       fi
+
+       echo
+       echo "${PTXDIST_LOG_PROMPT}done. There is no toolchain yet, select one 
with"
+       echo "${PTXDIST_LOG_PROMPT}'ptxdist toolchain <path>'. 'ptxdist 
platformconfig' refines"
+       echo "${PTXDIST_LOG_PROMPT}the platform, 'ptxdist newpackage <type>' 
adds own packages."
+       echo
+}
+
 
 #
 # guess and find the toolchain
diff --git a/doc/ref_parameter.rst b/doc/ref_parameter.rst
index e167f28fe..52d470304 100644
--- a/doc/ref_parameter.rst
+++ b/doc/ref_parameter.rst
@@ -28,6 +28,8 @@ Setup and Project Actions
   the same project. The default location for the configuration file is
   ``configs/ptxconfig``. PTXdist will use this if no other configuration is
   selected.
+  If there is no configuration at all and PTXdist runs in a terminal, it
+  offers to create a new project instead, see ``rules/templates/project/``.
 
 ``platform <config>``
   this action will select a platform
@@ -38,6 +40,8 @@ Setup and Project Actions
   The default location for the configuration file is
   ``configs/*/platformconfig``. PTXdist will use that if the pattern matches
   exactly one file and no other configuration is selected.
+  If no platform is selected and PTXdist runs in a terminal, it offers to
+  create a new one instead.
 
 ``toolchain [<path>]``
   this action will select the toolchain to use. If no path is specified
diff --git a/rules/templates/project/gitignore 
b/rules/templates/project/gitignore
new file mode 100644
index 000000000..20ede9441
--- /dev/null
+++ b/rules/templates/project/gitignore
@@ -0,0 +1,9 @@
+/.ptxdist/
+/configs/*.old
+/configs/platform-*/*.old
+/platform-*
+/selected_collectionconfig
+/selected_platformconfig
+/selected_ptxconfig
+/selected_toolchain*
+/src
diff --git a/rules/templates/project/platformconfig 
b/rules/templates/project/platformconfig
new file mode 100644
index 000000000..165143199
--- /dev/null
+++ b/rules/templates/project/platformconfig
@@ -0,0 +1,10 @@
+#
+# template for a new project, everything not set here gets its default
+#
+PTXCONF__platformconfig_MAGIC__=y
+PTXCONF_PLATFORMCONFIG_VERSION="@PTXDIST_VERSION_FULL@"
+PTXCONF_PLATFORM="@PLATFORM@"
+PTXCONF_@ARCH@=y
+# no toolchain yet, select one with 'ptxdist toolchain <path>'
+PTXCONF_CROSSCHAIN_VENDOR=""
+PTXCONF_CROSSCHAIN_CHECK=""
diff --git a/rules/templates/project/ptxconfig 
b/rules/templates/project/ptxconfig
new file mode 100644
index 000000000..2b4b71024
--- /dev/null
+++ b/rules/templates/project/ptxconfig
@@ -0,0 +1,6 @@
+#
+# template for a new project, everything not set here gets its default
+#
+PTXCONF__ptxconfig_MAGIC__=y
+PTXCONF_CONFIGFILE_VERSION="@PTXDIST_VERSION_FULL@"
+PTXCONF_PROJECT="@PROJECT@"
-- 
2.47.3


Reply via email to