<commit_before>package appjson

import (
	"fmt"
	"io"
	"io/ioutil"
	"net/http"
	"net/url"
	"os"
	"path"
	"path/filepath"
	"strings"

	"github.com/spf13/cobra"

	corev1 "k8s.io/api/core/v1"
	"k8s.io/apimachinery/pkg/api/meta"
	"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
	"k8s.io/apimachinery/pkg/runtime"
	"k8s.io/apimachinery/pkg/runtime/schema"
	kerrors "k8s.io/apimachinery/pkg/util/errors"
	"k8s.io/client-go/dynamic"
	"k8s.io/client-go/kubernetes"
	"k8s.io/client-go/rest"
	"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
	kcmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions/printers"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions/resource"
	"k8s.io/kubernetes/pkg/kubectl/scheme"

	"github.com/openshift/origin/pkg/oc/lib/newapp/appjson"
	appcmd "github.com/openshift/origin/pkg/oc/lib/newapp/cmd"
	"github.com/openshift/origin/pkg/oc/util/ocscheme"
	templatev1client "github.com/openshift/origin/pkg/template/client/v1"
)

const AppJSONV1GeneratorName = "app-json/v1"

var (
	appJSONLong = templates.LongDesc(`
		Import app.json files as OpenShift objects

		app.json defines the pattern of a simple, stateless web application that can be horizontally scaled.
		This command will transform a provided app.json object into its OpenShift equivalent.
		During transformation fields in the app.json syntax that are not relevant when running on top of
		a containerized platform will be ignored and a warning printed.

		The command will create objects unless you pass the -o yaml or --as-template flags to generate a
		configuration file for later use.

		Experimental: This command is under active development and may change without notice.`)

	appJSONExample = templates.Examples(`
		# Import a directory containing an app.json file
	  $ %[1]s app.json -f .

	  # Turn an app.json file into a template
	  $ %[1]s app.json -f ./app.json -o yaml --as-template`)
)

type AppJSONOptions struct {
	PrintFlags *genericclioptions.PrintFlags

	Printer printers.ResourcePrinter

	BaseImage        string
	Generator        string
	AsTemplate       string
	OutputVersionStr string

	OutputVersions []schema.GroupVersion

	Namespace     string
	RESTMapper    meta.RESTMapper
	DynamicClient dynamic.Interface
	Client        rest.Interface

	genericclioptions.IOStreams
	resource.FilenameOptions
}

func NewAppJSONOptions(streams genericclioptions.IOStreams) *AppJSONOptions {
	return &AppJSONOptions{
		IOStreams:  streams,
		PrintFlags: genericclioptions.NewPrintFlags("created").WithTypeSetter(ocscheme.PrintingInternalScheme),
		Generator:  AppJSONV1GeneratorName,
	}
}

// NewCmdAppJSON imports an app.json file (schema described here: https://devcenter.heroku.com/articles/app-json-schema)
// as a template.
func NewCmdAppJSON(fullName string, f kcmdutil.Factory, streams genericclioptions.IOStreams) *cobra.Command {
	o := NewAppJSONOptions(streams)
	cmd := &cobra.Command{
		Use:     "app.json -f APPJSON",
		Short:   "Import an app.json definition into OpenShift (experimental)",
		Long:    appJSONLong,
		Example: fmt.Sprintf(appJSONExample, fullName),
		Run: func(cmd *cobra.Command, args []string) {
			kcmdutil.CheckErr(o.Complete(f, cmd, args))
			kcmdutil.CheckErr(o.Validate())
			kcmdutil.CheckErr(o.Run())
		},
	}
	usage := "Filename, directory, or URL to app.json file to use"
	kcmdutil.AddJsonFilenameFlag(cmd.Flags(), &o.Filenames, usage)
	cmd.MarkFlagRequired("filename")
	cmd.Flags().StringVar(&o.BaseImage, "image", o.BaseImage, "An optional image to use as your base Docker build (must have ONBUILD directives)")
	cmd.Flags().StringVar(&o.Generator, "generator", o.Generator, "The name of the generator strategy to use - specify this value to for backwards compatibility.")
	cmd.Flags().StringVar(&o.AsTemplate, "as-template", o.AsTemplate, "If set, generate a template with the provided name")
	cmd.Flags().StringVar(&o.OutputVersionStr, "output-version", o.OutputVersionStr, "The preferred API versions of the output objects")

	o.PrintFlags.AddFlags(cmd)
	return cmd
}

func (o *AppJSONOptions) createResources(list *corev1.List) (*corev1.List, []error) {
	errors := []error{}
	created := &corev1.List{}

	for i, item := range list.Items {
		var err error
		unstructuredObj := &unstructured.Unstructured{}
		unstructuredObj.Object, err = runtime.DefaultUnstructuredConverter.ToUnstructured(item)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		mapping, err := o.RESTMapper.RESTMapping(unstructuredObj.GroupVersionKind().GroupKind(), unstructuredObj.GroupVersionKind().Version)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		_, err = o.DynamicClient.Resource(mapping.Resource).Namespace(o.Namespace).Create(unstructuredObj)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		created.Items = append(created.Items, list.Items[i])
	}

	return created, errors
}

func (o *AppJSONOptions) Complete(f kcmdutil.Factory, cmd *cobra.Command, args []string) error {
	for _, v := range strings.Split(o.OutputVersionStr, ",") {
		gv, err := schema.ParseGroupVersion(v)
		if err != nil {
			return fmt.Errorf("provided output-version %q is not valid: %v", v, err)
		}
		o.OutputVersions = append(o.OutputVersions, gv)
	}
	o.OutputVersions = append(o.OutputVersions, scheme.Scheme.PrioritizedVersionsAllGroups()...)

	clientConfig, err := f.ToRESTConfig()
	if err != nil {
		return err
	}

	o.RESTMapper, err = f.ToRESTMapper()
	if err != nil {
		return err
	}

	o.DynamicClient, err = dynamic.NewForConfig(clientConfig)

	o.Printer, err = o.PrintFlags.ToPrinter()
	if err != nil {
		return err
	}

	o.Namespace, _, err = f.ToRawKubeConfigLoader().Namespace()
	if err != nil {
		return err
	}

	clientset, err := kubernetes.NewForConfig(clientConfig)
	if err != nil {
		return err
	}

	o.Client = clientset.CoreV1().RESTClient()
	if err != nil {
		return err
	}

	return nil
}

func (o *AppJSONOptions) Validate() error {
	if len(o.Filenames) != 1 {
		return fmt.Errorf("you must provide the path to an app.json file or directory containing app.json")
	}
	switch o.Generator {
	case AppJSONV1GeneratorName:
	default:
		return fmt.Errorf("the generator %q is not supported, use: %s", o.Generator, AppJSONV1GeneratorName)
	}
	return nil
}

func (o *AppJSONOptions) Run() error {
	localPath, contents, err := contentsForPathOrURL(o.Filenames[0], o.In, "app.json")
	if err != nil {
		return err
	}

	g := &appjson.Generator{
		LocalPath: localPath,
		BaseImage: o.BaseImage,
	}
	switch {
	case len(o.AsTemplate) > 0:
		g.Name = o.AsTemplate
	case len(localPath) > 0:
		g.Name = filepath.Base(localPath)
	default:
		g.Name = path.Base(path.Dir(o.Filenames[0]))
	}
	if len(g.Name) == 0 {
		g.Name = "app"
	}

	template, err := g.Generate(contents)
	if err != nil {
		return err
	}

	template.ObjectLabels = map[string]string{"app.json": template.Name}

	// TODO: stop implying --dry-run behavior when an --output value is provided
	if o.PrintFlags.OutputFormat != nil && len(*o.PrintFlags.OutputFormat) > 0 || len(o.AsTemplate) > 0 {
		var obj runtime.Object
		if len(o.AsTemplate) > 0 {
			template.Name = o.AsTemplate
			obj = template
		} else {
			obj = &corev1.List{Items: template.Objects}
		}
		return o.Printer.PrintObj(obj, o.Out)
	}

	templateProcessor := templatev1client.NewTemplateProcessorClient(o.Client, o.Namespace)
	result, err := appcmd.TransformTemplate(template, templateProcessor, o.Namespace, nil, false)
	if err != nil {
		return err
	}

	appcmd.DescribeGeneratedTemplate(o.Out, "", result, o.Namespace)

	objs := &corev1.List{Items: result.Objects}

	// actually create the objects
	created, errs := o.createResources(objs)

	// print what we have created first, then return a potential set of errors
	if err := o.Printer.PrintObj(created, o.Out); err != nil {
		errs = append(errs, err)
	}

	return kerrors.NewAggregate(errs)
}

func contentsForPathOrURL(s string, in io.Reader, subpaths ...string) (string, []byte, error) {
	switch {
	case s == "-":
		contents, err := ioutil.ReadAll(in)
		return "", contents, err
	case strings.Index(s, "http://") == 0 || strings.Index(s, "https://") == 0:
		_, err := url.Parse(s)
		if err != nil {
			return "", nil, fmt.Errorf("the URL passed to filename %q is not valid: %v", s, err)
		}
		res, err := http.Get(s)
		if err != nil {
			return "", nil, err
		}
		defer res.Body.Close()
		contents, err := ioutil.ReadAll(res.Body)
		return "", contents, err
	default:
		stat, err := os.Stat(s)
		if err != nil {
			return s, nil, err
		}
		if !stat.IsDir() {
			contents, err := ioutil.ReadFile(s)
			return s, contents, err
		}
		for _, sub := range subpaths {
			path := filepath.Join(s, sub)
			stat, err := os.Stat(path)
			if err != nil {
				continue
			}
			if stat.IsDir() {
				continue
			}
			contents, err := ioutil.ReadFile(s)
			return path, contents, err
		}
		return s, nil, os.ErrNotExist
	}
}
<commit_msg>Deprecate output-version in import app.json<commit_after>package appjson

import (
	"fmt"
	"io"
	"io/ioutil"
	"net/http"
	"net/url"
	"os"
	"path"
	"path/filepath"
	"strings"

	"github.com/spf13/cobra"

	corev1 "k8s.io/api/core/v1"
	"k8s.io/apimachinery/pkg/api/meta"
	"k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
	"k8s.io/apimachinery/pkg/runtime"
	"k8s.io/apimachinery/pkg/runtime/schema"
	kerrors "k8s.io/apimachinery/pkg/util/errors"
	"k8s.io/client-go/dynamic"
	"k8s.io/client-go/kubernetes"
	"k8s.io/client-go/rest"
	"k8s.io/kubernetes/pkg/kubectl/cmd/templates"
	kcmdutil "k8s.io/kubernetes/pkg/kubectl/cmd/util"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions/printers"
	"k8s.io/kubernetes/pkg/kubectl/genericclioptions/resource"
	"k8s.io/kubernetes/pkg/kubectl/scheme"

	"github.com/openshift/origin/pkg/oc/lib/newapp/appjson"
	appcmd "github.com/openshift/origin/pkg/oc/lib/newapp/cmd"
	"github.com/openshift/origin/pkg/oc/util/ocscheme"
	templatev1client "github.com/openshift/origin/pkg/template/client/v1"
)

const AppJSONV1GeneratorName = "app-json/v1"

var (
	appJSONLong = templates.LongDesc(`
		Import app.json files as OpenShift objects

		app.json defines the pattern of a simple, stateless web application that can be horizontally scaled.
		This command will transform a provided app.json object into its OpenShift equivalent.
		During transformation fields in the app.json syntax that are not relevant when running on top of
		a containerized platform will be ignored and a warning printed.

		The command will create objects unless you pass the -o yaml or --as-template flags to generate a
		configuration file for later use.

		Experimental: This command is under active development and may change without notice.`)

	appJSONExample = templates.Examples(`
		# Import a directory containing an app.json file
	  $ %[1]s app.json -f .

	  # Turn an app.json file into a template
	  $ %[1]s app.json -f ./app.json -o yaml --as-template`)
)

type AppJSONOptions struct {
	PrintFlags *genericclioptions.PrintFlags

	Printer printers.ResourcePrinter

	BaseImage        string
	Generator        string
	AsTemplate       string
	OutputVersionStr string

	OutputVersions []schema.GroupVersion

	Namespace     string
	RESTMapper    meta.RESTMapper
	DynamicClient dynamic.Interface
	Client        rest.Interface

	genericclioptions.IOStreams
	resource.FilenameOptions
}

func NewAppJSONOptions(streams genericclioptions.IOStreams) *AppJSONOptions {
	return &AppJSONOptions{
		IOStreams:  streams,
		PrintFlags: genericclioptions.NewPrintFlags("created").WithTypeSetter(ocscheme.PrintingInternalScheme),
		Generator:  AppJSONV1GeneratorName,
	}
}

// NewCmdAppJSON imports an app.json file (schema described here: https://devcenter.heroku.com/articles/app-json-schema)
// as a template.
func NewCmdAppJSON(fullName string, f kcmdutil.Factory, streams genericclioptions.IOStreams) *cobra.Command {
	o := NewAppJSONOptions(streams)
	cmd := &cobra.Command{
		Use:     "app.json -f APPJSON",
		Short:   "Import an app.json definition into OpenShift (experimental)",
		Long:    appJSONLong,
		Example: fmt.Sprintf(appJSONExample, fullName),
		Run: func(cmd *cobra.Command, args []string) {
			kcmdutil.CheckErr(o.Complete(f, cmd, args))
			kcmdutil.CheckErr(o.Validate())
			kcmdutil.CheckErr(o.Run())
		},
	}
	usage := "Filename, directory, or URL to app.json file to use"
	kcmdutil.AddJsonFilenameFlag(cmd.Flags(), &o.Filenames, usage)
	cmd.MarkFlagRequired("filename")
	cmd.Flags().StringVar(&o.BaseImage, "image", o.BaseImage, "An optional image to use as your base Docker build (must have ONBUILD directives)")
	cmd.Flags().StringVar(&o.Generator, "generator", o.Generator, "The name of the generator strategy to use - specify this value to for backwards compatibility.")
	cmd.Flags().StringVar(&o.AsTemplate, "as-template", o.AsTemplate, "If set, generate a template with the provided name")
	cmd.Flags().StringVar(&o.OutputVersionStr, "output-version", o.OutputVersionStr, "The preferred API versions of the output objects")
	cmd.Flags().MarkDeprecated("output-version", "this flag is deprecated and will be removed in the future")

	o.PrintFlags.AddFlags(cmd)
	return cmd
}

func (o *AppJSONOptions) createResources(list *corev1.List) (*corev1.List, []error) {
	errors := []error{}
	created := &corev1.List{}

	for i, item := range list.Items {
		var err error
		unstructuredObj := &unstructured.Unstructured{}
		unstructuredObj.Object, err = runtime.DefaultUnstructuredConverter.ToUnstructured(item)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		mapping, err := o.RESTMapper.RESTMapping(unstructuredObj.GroupVersionKind().GroupKind(), unstructuredObj.GroupVersionKind().Version)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		_, err = o.DynamicClient.Resource(mapping.Resource).Namespace(o.Namespace).Create(unstructuredObj)
		if err != nil {
			errors = append(errors, err)
			continue
		}

		created.Items = append(created.Items, list.Items[i])
	}

	return created, errors
}

func (o *AppJSONOptions) Complete(f kcmdutil.Factory, cmd *cobra.Command, args []string) error {
	for _, v := range strings.Split(o.OutputVersionStr, ",") {
		gv, err := schema.ParseGroupVersion(v)
		if err != nil {
			return fmt.Errorf("provided output-version %q is not valid: %v", v, err)
		}
		o.OutputVersions = append(o.OutputVersions, gv)
	}
	o.OutputVersions = append(o.OutputVersions, scheme.Scheme.PrioritizedVersionsAllGroups()...)

	clientConfig, err := f.ToRESTConfig()
	if err != nil {
		return err
	}

	o.RESTMapper, err = f.ToRESTMapper()
	if err != nil {
		return err
	}

	o.DynamicClient, err = dynamic.NewForConfig(clientConfig)

	o.Printer, err = o.PrintFlags.ToPrinter()
	if err != nil {
		return err
	}

	o.Namespace, _, err = f.ToRawKubeConfigLoader().Namespace()
	if err != nil {
		return err
	}

	clientset, err := kubernetes.NewForConfig(clientConfig)
	if err != nil {
		return err
	}

	o.Client = clientset.CoreV1().RESTClient()
	if err != nil {
		return err
	}

	return nil
}

func (o *AppJSONOptions) Validate() error {
	if len(o.Filenames) != 1 {
		return fmt.Errorf("you must provide the path to an app.json file or directory containing app.json")
	}
	switch o.Generator {
	case AppJSONV1GeneratorName:
	default:
		return fmt.Errorf("the generator %q is not supported, use: %s", o.Generator, AppJSONV1GeneratorName)
	}
	return nil
}

func (o *AppJSONOptions) Run() error {
	localPath, contents, err := contentsForPathOrURL(o.Filenames[0], o.In, "app.json")
	if err != nil {
		return err
	}

	g := &appjson.Generator{
		LocalPath: localPath,
		BaseImage: o.BaseImage,
	}
	switch {
	case len(o.AsTemplate) > 0:
		g.Name = o.AsTemplate
	case len(localPath) > 0:
		g.Name = filepath.Base(localPath)
	default:
		g.Name = path.Base(path.Dir(o.Filenames[0]))
	}
	if len(g.Name) == 0 {
		g.Name = "app"
	}

	template, err := g.Generate(contents)
	if err != nil {
		return err
	}

	template.ObjectLabels = map[string]string{"app.json": template.Name}

	// TODO: stop implying --dry-run behavior when an --output value is provided
	if o.PrintFlags.OutputFormat != nil && len(*o.PrintFlags.OutputFormat) > 0 || len(o.AsTemplate) > 0 {
		var obj runtime.Object
		if len(o.AsTemplate) > 0 {
			template.Name = o.AsTemplate
			obj = template
		} else {
			obj = &corev1.List{Items: template.Objects}
		}
		return o.Printer.PrintObj(obj, o.Out)
	}

	templateProcessor := templatev1client.NewTemplateProcessorClient(o.Client, o.Namespace)
	result, err := appcmd.TransformTemplate(template, templateProcessor, o.Namespace, nil, false)
	if err != nil {
		return err
	}

	appcmd.DescribeGeneratedTemplate(o.Out, "", result, o.Namespace)

	objs := &corev1.List{Items: result.Objects}

	// actually create the objects
	created, errs := o.createResources(objs)

	// print what we have created first, then return a potential set of errors
	if err := o.Printer.PrintObj(created, o.Out); err != nil {
		errs = append(errs, err)
	}

	return kerrors.NewAggregate(errs)
}

func contentsForPathOrURL(s string, in io.Reader, subpaths ...string) (string, []byte, error) {
	switch {
	case s == "-":
		contents, err := ioutil.ReadAll(in)
		return "", contents, err
	case strings.Index(s, "http://") == 0 || strings.Index(s, "https://") == 0:
		_, err := url.Parse(s)
		if err != nil {
			return "", nil, fmt.Errorf("the URL passed to filename %q is not valid: %v", s, err)
		}
		res, err := http.Get(s)
		if err != nil {
			return "", nil, err
		}
		defer res.Body.Close()
		contents, err := ioutil.ReadAll(res.Body)
		return "", contents, err
	default:
		stat, err := os.Stat(s)
		if err != nil {
			return s, nil, err
		}
		if !stat.IsDir() {
			contents, err := ioutil.ReadFile(s)
			return s, contents, err
		}
		for _, sub := range subpaths {
			path := filepath.Join(s, sub)
			stat, err := os.Stat(path)
			if err != nil {
				continue
			}
			if stat.IsDir() {
				continue
			}
			contents, err := ioutil.ReadFile(s)
			return path, contents, err
		}
		return s, nil, os.ErrNotExist
	}
}
<|endoftext|>


<commit_before>/*
Copyright 2016 The Kubernetes Authors All rights reserved.

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.
*/

package etcd

import (
	"k8s.io/kubernetes/pkg/api"
	"k8s.io/kubernetes/pkg/apis/batch"
	"k8s.io/kubernetes/pkg/fields"
	"k8s.io/kubernetes/pkg/labels"
	"k8s.io/kubernetes/pkg/registry/cachesize"
	"k8s.io/kubernetes/pkg/registry/generic"
	"k8s.io/kubernetes/pkg/registry/generic/registry"
	"k8s.io/kubernetes/pkg/registry/scheduledjob"
	"k8s.io/kubernetes/pkg/runtime"
)

// REST implements a RESTStorage for scheduled jobs against etcd
type REST struct {
	*registry.Store
}

// NewREST returns a RESTStorage object that will work against ScheduledJobs.
func NewREST(opts generic.RESTOptions) (*REST, *StatusREST) {
	prefix := "/scheduledjobs"

	newListFunc := func() runtime.Object { return &batch.ScheduledJobList{} }
	storageInterface := opts.Decorator(
		opts.Storage, cachesize.GetWatchCacheSizeByResource(cachesize.ScheduledJobs), &batch.ScheduledJob{}, prefix, scheduledjob.Strategy, newListFunc)

	store := &registry.Store{
		NewFunc: func() runtime.Object { return &batch.ScheduledJob{} },

		// NewListFunc returns an object capable of storing results of an etcd list.
		NewListFunc: newListFunc,
		// Produces a path that etcd understands, to the root of the resource
		// by combining the namespace in the context with the given prefix
		KeyRootFunc: func(ctx api.Context) string {
			return registry.NamespaceKeyRootFunc(ctx, prefix)
		},
		// Produces a path that etcd understands, to the resource by combining
		// the namespace in the context with the given prefix
		KeyFunc: func(ctx api.Context, name string) (string, error) {
			return registry.NamespaceKeyFunc(ctx, prefix, name)
		},
		// Retrieve the name field of a scheduled job
		ObjectNameFunc: func(obj runtime.Object) (string, error) {
			return obj.(*batch.ScheduledJob).Name, nil
		},
		// Used to match objects based on labels/fields for list and watch
		PredicateFunc: func(label labels.Selector, field fields.Selector) generic.Matcher {
			return scheduledjob.MatchScheduledJob(label, field)
		},
		QualifiedResource:       batch.Resource("scheduledjobs"),
		DeleteCollectionWorkers: opts.DeleteCollectionWorkers,

		// Used to validate scheduled job creation
		CreateStrategy: scheduledjob.Strategy,

		// Used to validate scheduled job updates
		UpdateStrategy: scheduledjob.Strategy,
		DeleteStrategy: scheduledjob.Strategy,

		Storage: storageInterface,
	}

	statusStore := *store
	statusStore.UpdateStrategy = scheduledjob.StatusStrategy

	return &REST{store}, &StatusREST{store: &statusStore}
}

// StatusREST implements the REST endpoint for changing the status of a resourcequota.
type StatusREST struct {
	store *registry.Store
}

func (r *StatusREST) New() runtime.Object {
	return &batch.ScheduledJob{}
}

// Update alters the status subset of an object.
func (r *StatusREST) Update(ctx api.Context, obj runtime.Object) (runtime.Object, bool, error) {
	return r.store.Update(ctx, obj)
}
<commit_msg>fix go install ./pkg/...<commit_after>/*
Copyright 2016 The Kubernetes Authors All rights reserved.

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.
*/

package etcd

import (
	"k8s.io/kubernetes/pkg/api"
	"k8s.io/kubernetes/pkg/api/rest"
	"k8s.io/kubernetes/pkg/apis/batch"
	"k8s.io/kubernetes/pkg/fields"
	"k8s.io/kubernetes/pkg/labels"
	"k8s.io/kubernetes/pkg/registry/cachesize"
	"k8s.io/kubernetes/pkg/registry/generic"
	"k8s.io/kubernetes/pkg/registry/generic/registry"
	"k8s.io/kubernetes/pkg/registry/scheduledjob"
	"k8s.io/kubernetes/pkg/runtime"
)

// REST implements a RESTStorage for scheduled jobs against etcd
type REST struct {
	*registry.Store
}

// NewREST returns a RESTStorage object that will work against ScheduledJobs.
func NewREST(opts generic.RESTOptions) (*REST, *StatusREST) {
	prefix := "/scheduledjobs"

	newListFunc := func() runtime.Object { return &batch.ScheduledJobList{} }
	storageInterface := opts.Decorator(
		opts.Storage, cachesize.GetWatchCacheSizeByResource(cachesize.ScheduledJobs), &batch.ScheduledJob{}, prefix, scheduledjob.Strategy, newListFunc)

	store := &registry.Store{
		NewFunc: func() runtime.Object { return &batch.ScheduledJob{} },

		// NewListFunc returns an object capable of storing results of an etcd list.
		NewListFunc: newListFunc,
		// Produces a path that etcd understands, to the root of the resource
		// by combining the namespace in the context with the given prefix
		KeyRootFunc: func(ctx api.Context) string {
			return registry.NamespaceKeyRootFunc(ctx, prefix)
		},
		// Produces a path that etcd understands, to the resource by combining
		// the namespace in the context with the given prefix
		KeyFunc: func(ctx api.Context, name string) (string, error) {
			return registry.NamespaceKeyFunc(ctx, prefix, name)
		},
		// Retrieve the name field of a scheduled job
		ObjectNameFunc: func(obj runtime.Object) (string, error) {
			return obj.(*batch.ScheduledJob).Name, nil
		},
		// Used to match objects based on labels/fields for list and watch
		PredicateFunc: func(label labels.Selector, field fields.Selector) generic.Matcher {
			return scheduledjob.MatchScheduledJob(label, field)
		},
		QualifiedResource:       batch.Resource("scheduledjobs"),
		DeleteCollectionWorkers: opts.DeleteCollectionWorkers,

		// Used to validate scheduled job creation
		CreateStrategy: scheduledjob.Strategy,

		// Used to validate scheduled job updates
		UpdateStrategy: scheduledjob.Strategy,
		DeleteStrategy: scheduledjob.Strategy,

		Storage: storageInterface,
	}

	statusStore := *store
	statusStore.UpdateStrategy = scheduledjob.StatusStrategy

	return &REST{store}, &StatusREST{store: &statusStore}
}

// StatusREST implements the REST endpoint for changing the status of a resourcequota.
type StatusREST struct {
	store *registry.Store
}

func (r *StatusREST) New() runtime.Object {
	return &batch.ScheduledJob{}
}

// Update alters the status subset of an object.
func (r *StatusREST) Update(ctx api.Context, name string, objInfo rest.UpdatedObjectInfo) (runtime.Object, bool, error) {
	return r.store.Update(ctx, name, objInfo)
}
<|endoftext|>


<commit_before>package controller

import (
	"fmt"
	"github.com/Aptomi/aptomi/pkg/slinga/language"
	"github.com/Aptomi/aptomi/pkg/slinga/object"
	"github.com/Aptomi/aptomi/pkg/slinga/object/store"
	"sync"
)

const PolicyName = "policy"

type PolicyController interface {
	GetPolicy(object.Generation) (*language.Policy, error)
	GetPolicyData(object.Generation) (*PolicyData, error)
	GetPolicyFromData(policyData *PolicyData) (*language.Policy, error)
	UpdatePolicy([]object.Base) (bool, *PolicyData, error)
}

func NewPolicyController(store store.ObjectStore) PolicyController {
	return &PolicyControllerImpl{sync.Mutex{}, store}
}

var PolicyDataObject = &object.Info{
	Kind:        "policy",
	Versioned:   true,
	Constructor: func() object.Base { return &PolicyData{} },
}

type PolicyData struct {
	language.Metadata

	Objects map[string]map[string]object.Generation // kind -> name -> generation
}

func (p *PolicyData) Add(obj object.Base) {
	byKind, exist := p.Objects[obj.GetKind()]
	if !exist {
		byKind = make(map[string]object.Generation)
		p.Objects[obj.GetKind()] = byKind
	}
	byKind[obj.GetName()] = obj.GetGeneration()
}

type PolicyControllerImpl struct {
	update sync.Mutex
	store  store.ObjectStore
}

func (ctl *PolicyControllerImpl) GetPolicyData(gen object.Generation) (*PolicyData, error) {
	dataObj, err := ctl.store.GetByName(object.SystemNS, PolicyDataObject.Kind, PolicyName, gen)
	if err != nil {
		return nil, err
	}
	if dataObj == nil {
		return nil, nil
	}
	data, ok := dataObj.(*PolicyData)
	if !ok {
		return nil, fmt.Errorf("Unexpected type while getting PolicyData from DB")
	}
	return data, nil
}

func (ctl *PolicyControllerImpl) GetPolicyFromData(policyData *PolicyData) (*language.Policy, error) {
	policy := language.NewPolicy()

	// in case of first version of policy, we just need to have empty policy
	if policyData != nil && policyData.Objects != nil {
		for kind, nameGen := range policyData.Objects {
			for name, gen := range nameGen {
				obj, err := ctl.store.GetByName(object.SystemNS, kind, name, gen)
				if err != nil {
					return nil, err
				}
				policy.AddObject(obj)
			}
		}
	}
	return policy, nil
}

func (ctl *PolicyControllerImpl) GetPolicy(policyGen object.Generation) (*language.Policy, error) {
	policyData, err := ctl.GetPolicyData(policyGen)
	if err != nil {
		return nil, err
	}
	return ctl.GetPolicyFromData(policyData)
}

func (ctl *PolicyControllerImpl) UpdatePolicy(updatedObjects []object.Base) (bool, *PolicyData, error) {
	// we should process only a single policy update request at once
	ctl.update.Lock()
	defer ctl.update.Unlock()

	policyData, err := ctl.GetPolicyData(object.LastGen)
	if err != nil {
		return false, nil, err
	}

	changed := false

	// it could happen only for the fist time
	if policyData == nil {
		policyData = &PolicyData{
			Metadata: language.Metadata{
				Namespace: object.SystemNS,
				Kind:      PolicyDataObject.Kind,
				Name:      "policy",
			},
			Objects: make(map[string]map[string]object.Generation),
		}
		changed = true
	}

	for _, updatedObj := range updatedObjects {
		updated, err := ctl.store.Save(updatedObj)
		if err != nil {
			return false, nil, err
		}
		if updated {
			policyData.Add(updatedObj)
			changed = true
		}
	}

	if changed {
		_, err = ctl.store.Save(policyData)
		if err != nil {
			return false, nil, err
		}
	}

	// policy, err := ctl.getPolicyFromData(policyData)

	return changed, policyData, err
}
<commit_msg>Add todo to think about RWMutex for read/update policy instead of Mutex for update only<commit_after>package controller

import (
	"fmt"
	"github.com/Aptomi/aptomi/pkg/slinga/language"
	"github.com/Aptomi/aptomi/pkg/slinga/object"
	"github.com/Aptomi/aptomi/pkg/slinga/object/store"
	"sync"
)

const PolicyName = "policy"

type PolicyController interface {
	GetPolicy(object.Generation) (*language.Policy, error)
	GetPolicyData(object.Generation) (*PolicyData, error)
	GetPolicyFromData(policyData *PolicyData) (*language.Policy, error)
	UpdatePolicy([]object.Base) (bool, *PolicyData, error)
}

func NewPolicyController(store store.ObjectStore) PolicyController {
	return &PolicyControllerImpl{sync.Mutex{}, store}
}

var PolicyDataObject = &object.Info{
	Kind:        "policy",
	Versioned:   true,
	Constructor: func() object.Base { return &PolicyData{} },
}

type PolicyData struct {
	language.Metadata

	Objects map[string]map[string]object.Generation // kind -> name -> generation
}

func (p *PolicyData) Add(obj object.Base) {
	byKind, exist := p.Objects[obj.GetKind()]
	if !exist {
		byKind = make(map[string]object.Generation)
		p.Objects[obj.GetKind()] = byKind
	}
	byKind[obj.GetName()] = obj.GetGeneration()
}

type PolicyControllerImpl struct {
	update sync.Mutex
	store  store.ObjectStore
}

func (ctl *PolicyControllerImpl) GetPolicyData(gen object.Generation) (*PolicyData, error) {
	dataObj, err := ctl.store.GetByName(object.SystemNS, PolicyDataObject.Kind, PolicyName, gen)
	if err != nil {
		return nil, err
	}
	if dataObj == nil {
		return nil, nil
	}
	data, ok := dataObj.(*PolicyData)
	if !ok {
		return nil, fmt.Errorf("Unexpected type while getting PolicyData from DB")
	}
	return data, nil
}

func (ctl *PolicyControllerImpl) GetPolicyFromData(policyData *PolicyData) (*language.Policy, error) {
	policy := language.NewPolicy()

	// in case of first version of policy, we just need to have empty policy
	if policyData != nil && policyData.Objects != nil {
		for kind, nameGen := range policyData.Objects {
			for name, gen := range nameGen {
				obj, err := ctl.store.GetByName(object.SystemNS, kind, name, gen)
				if err != nil {
					return nil, err
				}
				policy.AddObject(obj)
			}
		}
	}
	return policy, nil
}

func (ctl *PolicyControllerImpl) GetPolicy(policyGen object.Generation) (*language.Policy, error) {
	// todo should we use RWMutex for get/update policy?
	policyData, err := ctl.GetPolicyData(policyGen)
	if err != nil {
		return nil, err
	}
	return ctl.GetPolicyFromData(policyData)
}

func (ctl *PolicyControllerImpl) UpdatePolicy(updatedObjects []object.Base) (bool, *PolicyData, error) {
	// we should process only a single policy update request at once
	ctl.update.Lock()
	defer ctl.update.Unlock()

	policyData, err := ctl.GetPolicyData(object.LastGen)
	if err != nil {
		return false, nil, err
	}

	changed := false

	// it could happen only for the fist time
	if policyData == nil {
		policyData = &PolicyData{
			Metadata: language.Metadata{
				Namespace: object.SystemNS,
				Kind:      PolicyDataObject.Kind,
				Name:      "policy",
			},
			Objects: make(map[string]map[string]object.Generation),
		}
		changed = true
	}

	for _, updatedObj := range updatedObjects {
		updated, err := ctl.store.Save(updatedObj)
		if err != nil {
			return false, nil, err
		}
		if updated {
			policyData.Add(updatedObj)
			changed = true
		}
	}

	if changed {
		_, err = ctl.store.Save(policyData)
		if err != nil {
			return false, nil, err
		}
	}

	// policy, err := ctl.getPolicyFromData(policyData)

	return changed, policyData, err
}
<|endoftext|>


<commit_before>package pixelgl

import (
	"github.com/faiface/glhf"
	"github.com/faiface/mainthread"
	"github.com/go-gl/mathgl/mgl32"
	"github.com/pkg/errors"
)

// glShader is a type to assist with managing a canvas's underlying
// shader configuration. This allows for customization of shaders on
// a per canvas basis.
type glShader struct {
	s      *glhf.Shader
	vf, uf glhf.AttrFormat
	vs, fs string

	uniforms []gsUniformAttr

	uniformDefaults struct {
		transform mgl32.Mat3
		colormask mgl32.Vec4
		bounds    mgl32.Vec4
		texbounds mgl32.Vec4
	}
}

type gsUniformAttr struct {
	Name      string
	Type      glhf.AttrType
	value     interface{}
	ispointer bool
}

// reinitialize GLShader data and recompile the underlying gl shader object
func (gs *glShader) update() {
	gs.uf = nil
	for _, u := range gs.uniforms {
		gs.uf = append(gs.uf, glhf.Attr{
			Name: u.Name,
			Type: u.Type,
		})
	}
	var shader *glhf.Shader
	mainthread.Call(func() {
		var err error
		shader, err = glhf.NewShader(
			gs.vf,
			gs.uf,
			gs.vs,
			gs.fs,
		)
		if err != nil {
			panic(errors.Wrap(err, "failed to create Canvas, there's a bug in the shader"))
		}
	})

	gs.s = shader
}

// gets the uniform index from GLShader
func (gs *glShader) getUniform(Name string) int {
	for i, u := range gs.uniforms {
		if u.Name == Name {
			return i
		}
	}
	return -1
}

// SetUniform appends a custom uniform name and value to the shader.
// if the uniform already exists, it will simply be overwritten.
//
// example:
//
//   utime := float32(time.Since(starttime)).Seconds())
//   mycanvas.shader.AddUniform("u_time", &utime)
func (gs *glShader) setUniform(name string, value interface{}) {
	t, p := getAttrType(value)
	if loc := gs.getUniform(name); loc > -1 {
		gs.uniforms[loc].Name = name
		gs.uniforms[loc].Type = t
		gs.uniforms[loc].ispointer = p
		gs.uniforms[loc].value = value
		return
	}
	gs.uniforms = append(gs.uniforms, gsUniformAttr{
		Name:      name,
		Type:      t,
		ispointer: p,
		value:     value,
	})
}

// Sets up a base shader with everything needed for a Pixel
// canvas to render correctly. The defaults can be overridden
// by simply using the SetUniform function.
func baseShader(c *Canvas) {
	gs := &glShader{
		vf: defaultCanvasVertexFormat,
		vs: baseCanvasVertexShader,
		fs: baseCanvasFragmentShader,
	}

	gs.setUniform("uTransform", &gs.uniformDefaults.transform)
	gs.setUniform("uColorMask", &gs.uniformDefaults.colormask)
	gs.setUniform("uBounds", &gs.uniformDefaults.bounds)
	gs.setUniform("uTexBounds", &gs.uniformDefaults.texbounds)

	c.shader = gs
}

// Value returns the attribute's concrete value. If the stored value
// is a pointer, we return the dereferenced value.
func (gu *gsUniformAttr) Value() interface{} {
	if !gu.ispointer {
		return gu.value
	}
	switch gu.Type {
	case glhf.Vec2:
		return *gu.value.(*mgl32.Vec2)
	case glhf.Vec3:
		return *gu.value.(*mgl32.Vec3)
	case glhf.Vec4:
		return *gu.value.(*mgl32.Vec4)
	case glhf.Mat2:
		return *gu.value.(*mgl32.Mat2)
	case glhf.Mat23:
		return *gu.value.(*mgl32.Mat2x3)
	case glhf.Mat24:
		return *gu.value.(*mgl32.Mat2x4)
	case glhf.Mat3:
		return *gu.value.(*mgl32.Mat3)
	case glhf.Mat32:
		return *gu.value.(*mgl32.Mat3x2)
	case glhf.Mat34:
		return *gu.value.(*mgl32.Mat3x4)
	case glhf.Mat4:
		return *gu.value.(*mgl32.Mat4)
	case glhf.Mat42:
		return *gu.value.(*mgl32.Mat4x2)
	case glhf.Mat43:
		return *gu.value.(*mgl32.Mat4x3)
	case glhf.Int:
		return *gu.value.(*int32)
	case glhf.Float:
		return *gu.value.(*float32)
	default:
		panic("invalid attrtype")
	}
}

// Returns the type identifier for any (supported) attribute variable type
// and whether or not it is a pointer of that type.
func getAttrType(v interface{}) (glhf.AttrType, bool) {
	switch v.(type) {
	case int32:
		return glhf.Int, false
	case float32:
		return glhf.Float, false
	case mgl32.Vec2:
		return glhf.Vec2, false
	case mgl32.Vec3:
		return glhf.Vec3, false
	case mgl32.Vec4:
		return glhf.Vec4, false
	case mgl32.Mat2:
		return glhf.Mat2, false
	case mgl32.Mat2x3:
		return glhf.Mat23, false
	case mgl32.Mat2x4:
		return glhf.Mat24, false
	case mgl32.Mat3:
		return glhf.Mat3, false
	case mgl32.Mat3x2:
		return glhf.Mat32, false
	case mgl32.Mat3x4:
		return glhf.Mat34, false
	case mgl32.Mat4:
		return glhf.Mat4, false
	case mgl32.Mat4x2:
		return glhf.Mat42, false
	case mgl32.Mat4x3:
		return glhf.Mat43, false
	case *mgl32.Vec2:
		return glhf.Vec2, true
	case *mgl32.Vec3:
		return glhf.Vec3, true
	case *mgl32.Vec4:
		return glhf.Vec4, true
	case *mgl32.Mat2:
		return glhf.Mat2, true
	case *mgl32.Mat2x3:
		return glhf.Mat23, true
	case *mgl32.Mat2x4:
		return glhf.Mat24, true
	case *mgl32.Mat3:
		return glhf.Mat3, true
	case *mgl32.Mat3x2:
		return glhf.Mat32, true
	case *mgl32.Mat3x4:
		return glhf.Mat34, true
	case *mgl32.Mat4:
		return glhf.Mat4, true
	case *mgl32.Mat4x2:
		return glhf.Mat42, true
	case *mgl32.Mat4x3:
		return glhf.Mat43, true
	case *int32:
		return glhf.Int, true
	case *float32:
		return glhf.Float, true
	default:
		panic("invalid AttrType")
	}
}

var baseCanvasVertexShader = `
#version 330 core

in vec2  aPosition;
in vec4  aColor;
in vec2  aTexCoords;
in float aIntensity;

out vec4  vColor;
out vec2  vTexCoords;
out float vIntensity;

uniform mat3 uTransform;
uniform vec4 uBounds;

void main() {
	vec2 transPos = (uTransform * vec3(aPosition, 1.0)).xy;
	vec2 normPos = (transPos - uBounds.xy) / uBounds.zw * 2 - vec2(1, 1);
	gl_Position = vec4(normPos, 0.0, 1.0);
	vColor = aColor;
	vTexCoords = aTexCoords;
	vIntensity = aIntensity;
}
`

var baseCanvasFragmentShader = `
#version 330 core

in vec4  vColor;
in vec2  vTexCoords;
in float vIntensity;

out vec4 fragColor;

uniform vec4 uColorMask;
uniform vec4 uTexBounds;
uniform sampler2D uTexture;

void main() {
	if (vIntensity == 0) {
		fragColor = uColorMask * vColor;
	} else {
		fragColor = vec4(0, 0, 0, 0);
		fragColor += (1 - vIntensity) * vColor;
		vec2 t = (vTexCoords - uTexBounds.xy) / uTexBounds.zw;
		fragColor += vIntensity * vColor * texture(uTexture, t);
		fragColor *= uColorMask;
	}
}
`
<commit_msg>Added position as out variable from vertex shader.<commit_after>package pixelgl

import (
	"github.com/faiface/glhf"
	"github.com/faiface/mainthread"
	"github.com/go-gl/mathgl/mgl32"
	"github.com/pkg/errors"
)

// glShader is a type to assist with managing a canvas's underlying
// shader configuration. This allows for customization of shaders on
// a per canvas basis.
type glShader struct {
	s      *glhf.Shader
	vf, uf glhf.AttrFormat
	vs, fs string

	uniforms []gsUniformAttr

	uniformDefaults struct {
		transform mgl32.Mat3
		colormask mgl32.Vec4
		bounds    mgl32.Vec4
		texbounds mgl32.Vec4
	}
}

type gsUniformAttr struct {
	Name      string
	Type      glhf.AttrType
	value     interface{}
	ispointer bool
}

// reinitialize GLShader data and recompile the underlying gl shader object
func (gs *glShader) update() {
	gs.uf = nil
	for _, u := range gs.uniforms {
		gs.uf = append(gs.uf, glhf.Attr{
			Name: u.Name,
			Type: u.Type,
		})
	}
	var shader *glhf.Shader
	mainthread.Call(func() {
		var err error
		shader, err = glhf.NewShader(
			gs.vf,
			gs.uf,
			gs.vs,
			gs.fs,
		)
		if err != nil {
			panic(errors.Wrap(err, "failed to create Canvas, there's a bug in the shader"))
		}
	})

	gs.s = shader
}

// gets the uniform index from GLShader
func (gs *glShader) getUniform(Name string) int {
	for i, u := range gs.uniforms {
		if u.Name == Name {
			return i
		}
	}
	return -1
}

// SetUniform appends a custom uniform name and value to the shader.
// if the uniform already exists, it will simply be overwritten.
//
// example:
//
//   utime := float32(time.Since(starttime)).Seconds())
//   mycanvas.shader.AddUniform("u_time", &utime)
func (gs *glShader) setUniform(name string, value interface{}) {
	t, p := getAttrType(value)
	if loc := gs.getUniform(name); loc > -1 {
		gs.uniforms[loc].Name = name
		gs.uniforms[loc].Type = t
		gs.uniforms[loc].ispointer = p
		gs.uniforms[loc].value = value
		return
	}
	gs.uniforms = append(gs.uniforms, gsUniformAttr{
		Name:      name,
		Type:      t,
		ispointer: p,
		value:     value,
	})
}

// Sets up a base shader with everything needed for a Pixel
// canvas to render correctly. The defaults can be overridden
// by simply using the SetUniform function.
func baseShader(c *Canvas) {
	gs := &glShader{
		vf: defaultCanvasVertexFormat,
		vs: baseCanvasVertexShader,
		fs: baseCanvasFragmentShader,
	}

	gs.setUniform("uTransform", &gs.uniformDefaults.transform)
	gs.setUniform("uColorMask", &gs.uniformDefaults.colormask)
	gs.setUniform("uBounds", &gs.uniformDefaults.bounds)
	gs.setUniform("uTexBounds", &gs.uniformDefaults.texbounds)

	c.shader = gs
}

// Value returns the attribute's concrete value. If the stored value
// is a pointer, we return the dereferenced value.
func (gu *gsUniformAttr) Value() interface{} {
	if !gu.ispointer {
		return gu.value
	}
	switch gu.Type {
	case glhf.Vec2:
		return *gu.value.(*mgl32.Vec2)
	case glhf.Vec3:
		return *gu.value.(*mgl32.Vec3)
	case glhf.Vec4:
		return *gu.value.(*mgl32.Vec4)
	case glhf.Mat2:
		return *gu.value.(*mgl32.Mat2)
	case glhf.Mat23:
		return *gu.value.(*mgl32.Mat2x3)
	case glhf.Mat24:
		return *gu.value.(*mgl32.Mat2x4)
	case glhf.Mat3:
		return *gu.value.(*mgl32.Mat3)
	case glhf.Mat32:
		return *gu.value.(*mgl32.Mat3x2)
	case glhf.Mat34:
		return *gu.value.(*mgl32.Mat3x4)
	case glhf.Mat4:
		return *gu.value.(*mgl32.Mat4)
	case glhf.Mat42:
		return *gu.value.(*mgl32.Mat4x2)
	case glhf.Mat43:
		return *gu.value.(*mgl32.Mat4x3)
	case glhf.Int:
		return *gu.value.(*int32)
	case glhf.Float:
		return *gu.value.(*float32)
	default:
		panic("invalid attrtype")
	}
}

// Returns the type identifier for any (supported) attribute variable type
// and whether or not it is a pointer of that type.
func getAttrType(v interface{}) (glhf.AttrType, bool) {
	switch v.(type) {
	case int32:
		return glhf.Int, false
	case float32:
		return glhf.Float, false
	case mgl32.Vec2:
		return glhf.Vec2, false
	case mgl32.Vec3:
		return glhf.Vec3, false
	case mgl32.Vec4:
		return glhf.Vec4, false
	case mgl32.Mat2:
		return glhf.Mat2, false
	case mgl32.Mat2x3:
		return glhf.Mat23, false
	case mgl32.Mat2x4:
		return glhf.Mat24, false
	case mgl32.Mat3:
		return glhf.Mat3, false
	case mgl32.Mat3x2:
		return glhf.Mat32, false
	case mgl32.Mat3x4:
		return glhf.Mat34, false
	case mgl32.Mat4:
		return glhf.Mat4, false
	case mgl32.Mat4x2:
		return glhf.Mat42, false
	case mgl32.Mat4x3:
		return glhf.Mat43, false
	case *mgl32.Vec2:
		return glhf.Vec2, true
	case *mgl32.Vec3:
		return glhf.Vec3, true
	case *mgl32.Vec4:
		return glhf.Vec4, true
	case *mgl32.Mat2:
		return glhf.Mat2, true
	case *mgl32.Mat2x3:
		return glhf.Mat23, true
	case *mgl32.Mat2x4:
		return glhf.Mat24, true
	case *mgl32.Mat3:
		return glhf.Mat3, true
	case *mgl32.Mat3x2:
		return glhf.Mat32, true
	case *mgl32.Mat3x4:
		return glhf.Mat34, true
	case *mgl32.Mat4:
		return glhf.Mat4, true
	case *mgl32.Mat4x2:
		return glhf.Mat42, true
	case *mgl32.Mat4x3:
		return glhf.Mat43, true
	case *int32:
		return glhf.Int, true
	case *float32:
		return glhf.Float, true
	default:
		panic("invalid AttrType")
	}
}

var baseCanvasVertexShader = `
#version 330 core

in vec2  aPosition;
in vec4  aColor;
in vec2  aTexCoords;
in float aIntensity;

out vec4  vColor;
out vec2  vTexCoords;
out float vIntensity;
out vec2  vPosition;

uniform mat3 uTransform;
uniform vec4 uBounds;

void main() {
	vec2 transPos = (uTransform * vec3(aPosition, 1.0)).xy;
	vec2 normPos = (transPos - uBounds.xy) / uBounds.zw * 2 - vec2(1, 1);
	gl_Position = vec4(normPos, 0.0, 1.0);
	vColor = aColor;
	vPosition = aPosition;
	vTexCoords = aTexCoords;
	vIntensity = aIntensity;
}
`

var baseCanvasFragmentShader = `
#version 330 core

in vec4  vColor;
in vec2  vTexCoords;
in float vIntensity;

out vec4 fragColor;

uniform vec4 uColorMask;
uniform vec4 uTexBounds;
uniform sampler2D uTexture;

void main() {
	if (vIntensity == 0) {
		fragColor = uColorMask * vColor;
	} else {
		fragColor = vec4(0, 0, 0, 0);
		fragColor += (1 - vIntensity) * vColor;
		vec2 t = (vTexCoords - uTexBounds.xy) / uTexBounds.zw;
		fragColor += vIntensity * vColor * texture(uTexture, t);
		fragColor *= uColorMask;
	}
}
`
<|endoftext|>


<commit_before>package asset

// DefaultImages are the defualt images bootkube components use.
var DefaultImages = ImageVersions{
	Etcd:            "quay.io/coreos/etcd:v3.1.8",
	EtcdOperator:    "quay.io/coreos/etcd-operator:v0.4.2",
	Flannel:         "quay.io/coreos/flannel:v0.7.1-amd64",
	FlannelCNI:      "quay.io/coreos/flannel-cni:0.1.0",
	Calico:          "quay.io/calico/node:v1.3.0",
	CalicoCNI:       "quay.io/calico/cni:v1.9.1-4-g23fcd5f",
	Hyperkube:       "quay.io/coreos/hyperkube:v1.7.1_coreos.0",
	Kenc:            "quay.io/coreos/kenc:8f6e2e885f790030fbbb0496ea2a2d8830e58b8f",
	KubeDNS:         "gcr.io/google_containers/k8s-dns-kube-dns-amd64:1.14.4",
	KubeDNSMasq:     "gcr.io/google_containers/k8s-dns-dnsmasq-nanny-amd64:1.14.4",
	KubeDNSSidecar:  "gcr.io/google_containers/k8s-dns-sidecar-amd64:1.14.4",
	PodCheckpointer: "quay.io/coreos/pod-checkpointer:4e7a7dab10bc4d895b66c21656291c6e0b017248",
}
<commit_msg>kenc: bump to 0.0.2<commit_after>package asset

// DefaultImages are the defualt images bootkube components use.
var DefaultImages = ImageVersions{
	Etcd:            "quay.io/coreos/etcd:v3.1.8",
	EtcdOperator:    "quay.io/coreos/etcd-operator:v0.4.2",
	Flannel:         "quay.io/coreos/flannel:v0.7.1-amd64",
	FlannelCNI:      "quay.io/coreos/flannel-cni:0.1.0",
	Calico:          "quay.io/calico/node:v1.3.0",
	CalicoCNI:       "quay.io/calico/cni:v1.9.1-4-g23fcd5f",
	Hyperkube:       "quay.io/coreos/hyperkube:v1.7.1_coreos.0",
	Kenc:            "quay.io/coreos/kenc:0.0.2",
	KubeDNS:         "gcr.io/google_containers/k8s-dns-kube-dns-amd64:1.14.4",
	KubeDNSMasq:     "gcr.io/google_containers/k8s-dns-dnsmasq-nanny-amd64:1.14.4",
	KubeDNSSidecar:  "gcr.io/google_containers/k8s-dns-sidecar-amd64:1.14.4",
	PodCheckpointer: "quay.io/coreos/pod-checkpointer:4e7a7dab10bc4d895b66c21656291c6e0b017248",
}
<|endoftext|>


<commit_before>// Copyright (C) 2015 Scaleway. All rights reserved.
// Use of this source code is governed by a MIT-style
// license that can be found in the LICENSE.md file.

package commands

import (
	"fmt"
	"os/exec"

	"github.com/scaleway/scaleway-cli/pkg/api"
	"github.com/scaleway/scaleway-cli/pkg/utils"
	"github.com/scaleway/scaleway-cli/vendor/github.com/Sirupsen/logrus"
)

// TopArgs are flags for the `RunTop` function
type TopArgs struct {
	Server  string
	Gateway string
}

// RunTop is the handler for 'scw top'
func RunTop(ctx CommandContext, args TopArgs) error {
	serverID := ctx.API.GetServerID(args.Server)
	command := "ps"
	server, err := ctx.API.GetServer(serverID)
	if err != nil {
		return fmt.Errorf("failed to get server information for %s: %v", serverID, err)
	}

	// Resolve gateway
	if args.Gateway == "" {
		args.Gateway = ctx.Getenv("SCW_GATEWAY")
	}
	var gateway string
	if args.Gateway == serverID || args.Gateway == args.Server {
		gateway = ""
	} else {
		gateway, err = api.ResolveGateway(ctx.API, args.Gateway)
		if err != nil {
			return fmt.Errorf("cannot resolve Gateway '%s': %v", args.Gateway, err)
		}
	}

	sshCommand := utils.NewSSHExecCmd(server.PublicAddress.IP, server.PrivateIP, true, []string{command}, gateway)
	logrus.Debugf("Executing: %s", sshCommand)
	out, err := exec.Command("ssh", sshCommand.Slice()[1:]...).CombinedOutput()
	if err != nil {
		fmt.Fprintf(ctx.Stdout, "%s", out)
	}
	return err
}
<commit_msg>use == instead of != top.go<commit_after>// Copyright (C) 2015 Scaleway. All rights reserved.
// Use of this source code is governed by a MIT-style
// license that can be found in the LICENSE.md file.

package commands

import (
	"fmt"
	"os/exec"

	"github.com/scaleway/scaleway-cli/pkg/api"
	"github.com/scaleway/scaleway-cli/pkg/utils"
	"github.com/scaleway/scaleway-cli/vendor/github.com/Sirupsen/logrus"
)

// TopArgs are flags for the `RunTop` function
type TopArgs struct {
	Server  string
	Gateway string
}

// RunTop is the handler for 'scw top'
func RunTop(ctx CommandContext, args TopArgs) error {
	serverID := ctx.API.GetServerID(args.Server)
	command := "ps"
	server, err := ctx.API.GetServer(serverID)
	if err != nil {
		return fmt.Errorf("failed to get server information for %s: %v", serverID, err)
	}

	// Resolve gateway
	if args.Gateway == "" {
		args.Gateway = ctx.Getenv("SCW_GATEWAY")
	}
	var gateway string
	if args.Gateway == serverID || args.Gateway == args.Server {
		gateway = ""
	} else {
		gateway, err = api.ResolveGateway(ctx.API, args.Gateway)
		if err != nil {
			return fmt.Errorf("cannot resolve Gateway '%s': %v", args.Gateway, err)
		}
	}

	sshCommand := utils.NewSSHExecCmd(server.PublicAddress.IP, server.PrivateIP, true, []string{command}, gateway)
	logrus.Debugf("Executing: %s", sshCommand)
	out, err := exec.Command("ssh", sshCommand.Slice()[1:]...).CombinedOutput()
	if err == nil {
		fmt.Fprintf(ctx.Stdout, "%s", out)
	}
	return err
}
<|endoftext|>


<commit_before>package servers

import (
	"encoding/base64"
	"encoding/json"
	"net/http"
	"testing"

	"github.com/rackspace/gophercloud/pagination"
	th "github.com/rackspace/gophercloud/testhelper"
	"github.com/rackspace/gophercloud/testhelper/client"
)

func TestListServers(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerListSuccessfully(t)

	pages := 0
	err := List(client.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractServers(page)
		if err != nil {
			return false, err
		}

		if len(actual) != 2 {
			t.Fatalf("Expected 2 servers, got %d", len(actual))
		}
		th.CheckDeepEquals(t, ServerHerp, actual[0])
		th.CheckDeepEquals(t, ServerDerp, actual[1])

		return true, nil
	})

	th.AssertNoErr(t, err)

	if pages != 1 {
		t.Errorf("Expected 1 page, saw %d", pages)
	}
}

func TestListAllServers(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerListSuccessfully(t)

	allPages, err := List(client.ServiceClient(), ListOpts{}).AllPages()
	th.AssertNoErr(t, err)
	actual, err := ExtractServers(allPages)
	th.AssertNoErr(t, err)
	th.CheckDeepEquals(t, ServerHerp, actual[0])
	th.CheckDeepEquals(t, ServerDerp, actual[1])
}

func TestCreateServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerCreationSuccessfully(t, SingleServerBody)

	actual, err := Create(client.ServiceClient(), CreateOpts{
		Name:      "derp",
		ImageRef:  "f90f6034-2570-4974-8351-6b49732ef2eb",
		FlavorRef: "1",
	}).Extract()
	th.AssertNoErr(t, err)

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestDeleteServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerDeletionSuccessfully(t)

	res := Delete(client.ServiceClient(), "asdfasdfasdf")
	th.AssertNoErr(t, res.Err)
}

func TestGetServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerGetSuccessfully(t)

	client := client.ServiceClient()
	actual, err := Get(client, "1234asdf").Extract()
	if err != nil {
		t.Fatalf("Unexpected Get error: %v", err)
	}

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestUpdateServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerUpdateSuccessfully(t)

	client := client.ServiceClient()
	actual, err := Update(client, "1234asdf", UpdateOpts{Name: "new-name"}).Extract()
	if err != nil {
		t.Fatalf("Unexpected Update error: %v", err)
	}

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestChangeServerAdminPassword(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleAdminPasswordChangeSuccessfully(t)

	res := ChangeAdminPassword(client.ServiceClient(), "1234asdf", "new-password")
	th.AssertNoErr(t, res.Err)
}

func TestRebootServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleRebootSuccessfully(t)

	res := Reboot(client.ServiceClient(), "1234asdf", SoftReboot)
	th.AssertNoErr(t, res.Err)
}

func TestRebuildServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleRebuildSuccessfully(t, SingleServerBody)

	opts := RebuildOpts{
		Name:       "new-name",
		AdminPass:  "swordfish",
		ImageID:    "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
		AccessIPv4: "1.2.3.4",
	}

	actual, err := Rebuild(client.ServiceClient(), "1234asdf", opts).Extract()
	th.AssertNoErr(t, err)

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestResizeServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "resize": { "flavorRef": "2" } }`)

		w.WriteHeader(http.StatusAccepted)
	})

	res := Resize(client.ServiceClient(), "1234asdf", ResizeOpts{FlavorRef: "2"})
	th.AssertNoErr(t, res.Err)
}

func TestConfirmResize(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "confirmResize": null }`)

		w.WriteHeader(http.StatusNoContent)
	})

	res := ConfirmResize(client.ServiceClient(), "1234asdf")
	th.AssertNoErr(t, res.Err)
}

func TestRevertResize(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "revertResize": null }`)

		w.WriteHeader(http.StatusAccepted)
	})

	res := RevertResize(client.ServiceClient(), "1234asdf")
	th.AssertNoErr(t, res.Err)
}

func TestRescue(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleServerRescueSuccessfully(t)

	res := Rescue(client.ServiceClient(), "1234asdf", RescueOpts{
		AdminPass: "1234567890",
	})
	th.AssertNoErr(t, res.Err)
	adminPass, _ := res.Extract()
	th.AssertEquals(t, "1234567890", adminPass)
}

func TestGetMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumGetSuccessfully(t)

	expected := map[string]string{"foo": "bar"}
	actual, err := Metadatum(client.ServiceClient(), "1234asdf", "foo").Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestCreateMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumCreateSuccessfully(t)

	expected := map[string]string{"foo": "bar"}
	actual, err := CreateMetadatum(client.ServiceClient(), "1234asdf", MetadatumOpts{"foo": "bar"}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestDeleteMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumDeleteSuccessfully(t)

	err := DeleteMetadatum(client.ServiceClient(), "1234asdf", "foo").ExtractErr()
	th.AssertNoErr(t, err)
}

func TestGetMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataGetSuccessfully(t)

	expected := map[string]string{"foo": "bar", "this": "that"}
	actual, err := Metadata(client.ServiceClient(), "1234asdf").Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestResetMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataResetSuccessfully(t)

	expected := map[string]string{"foo": "bar", "this": "that"}
	actual, err := ResetMetadata(client.ServiceClient(), "1234asdf", MetadataOpts{
		"foo":  "bar",
		"this": "that",
	}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestUpdateMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataUpdateSuccessfully(t)

	expected := map[string]string{"foo": "baz", "this": "those"}
	actual, err := UpdateMetadata(client.ServiceClient(), "1234asdf", MetadataOpts{
		"foo":  "baz",
		"this": "those",
	}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestListAddresses(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleAddressListSuccessfully(t)

	expected := ListAddressesExpected
	pages := 0
	err := ListAddresses(client.ServiceClient(), "asdfasdfasdf").EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractAddresses(page)
		th.AssertNoErr(t, err)

		if len(actual) != 2 {
			t.Fatalf("Expected 2 networks, got %d", len(actual))
		}
		th.CheckDeepEquals(t, expected, actual)

		return true, nil
	})
	th.AssertNoErr(t, err)
	th.CheckEquals(t, 1, pages)
}

func TestListAddressesByNetwork(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleNetworkAddressListSuccessfully(t)

	expected := ListNetworkAddressesExpected
	pages := 0
	err := ListAddressesByNetwork(client.ServiceClient(), "asdfasdfasdf", "public").EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractNetworkAddresses(page)
		th.AssertNoErr(t, err)

		if len(actual) != 2 {
			t.Fatalf("Expected 2 addresses, got %d", len(actual))
		}
		th.CheckDeepEquals(t, expected, actual)

		return true, nil
	})
	th.AssertNoErr(t, err)
	th.CheckEquals(t, 1, pages)
}

func TestCreateServerImage(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleCreateServerImageSuccessfully(t)

	_, err := CreateImage(client.ServiceClient(), "serverimage", CreateImageOpts{Name: "test"}).ExtractImageID()
	th.AssertNoErr(t, err)
}

func TestMarshalPersonality(t *testing.T) {
	name := "/etc/test"
	contents := []byte("asdfasdf")

	personality := Personality{
		&File{
			Path:     name,
			Contents: contents,
		},
	}

	data, err := json.Marshal(personality)
	if err != nil {
		t.Fatal(err)
	}

	var actual []map[string]string
	err = json.Unmarshal(data, &actual)
	if err != nil {
		t.Fatal(err)
	}

	if len(actual) != 1 {
		t.Fatal("expected personality length 1")
	}

	if actual[0]["path"] != name {
		t.Fatal("file path incorrect")
	}

	if actual[0]["contents"] != base64.StdEncoding.EncodeToString(contents) {
		t.Fatal("file contents incorrect")
	}
}

func TestCreateServerImage(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleCreateServerImageSuccessfully(t)

	_, err := CreateImage(client.ServiceClient(), "serverimage", CreateImageOpts{Name: "test"}).ExtractImageID()
	th.AssertNoErr(t, err)
}
<commit_msg>remove duplicate test from bad merge<commit_after>package servers

import (
	"encoding/base64"
	"encoding/json"
	"net/http"
	"testing"

	"github.com/rackspace/gophercloud/pagination"
	th "github.com/rackspace/gophercloud/testhelper"
	"github.com/rackspace/gophercloud/testhelper/client"
)

func TestListServers(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerListSuccessfully(t)

	pages := 0
	err := List(client.ServiceClient(), ListOpts{}).EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractServers(page)
		if err != nil {
			return false, err
		}

		if len(actual) != 2 {
			t.Fatalf("Expected 2 servers, got %d", len(actual))
		}
		th.CheckDeepEquals(t, ServerHerp, actual[0])
		th.CheckDeepEquals(t, ServerDerp, actual[1])

		return true, nil
	})

	th.AssertNoErr(t, err)

	if pages != 1 {
		t.Errorf("Expected 1 page, saw %d", pages)
	}
}

func TestListAllServers(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerListSuccessfully(t)

	allPages, err := List(client.ServiceClient(), ListOpts{}).AllPages()
	th.AssertNoErr(t, err)
	actual, err := ExtractServers(allPages)
	th.AssertNoErr(t, err)
	th.CheckDeepEquals(t, ServerHerp, actual[0])
	th.CheckDeepEquals(t, ServerDerp, actual[1])
}

func TestCreateServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerCreationSuccessfully(t, SingleServerBody)

	actual, err := Create(client.ServiceClient(), CreateOpts{
		Name:      "derp",
		ImageRef:  "f90f6034-2570-4974-8351-6b49732ef2eb",
		FlavorRef: "1",
	}).Extract()
	th.AssertNoErr(t, err)

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestDeleteServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerDeletionSuccessfully(t)

	res := Delete(client.ServiceClient(), "asdfasdfasdf")
	th.AssertNoErr(t, res.Err)
}

func TestGetServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerGetSuccessfully(t)

	client := client.ServiceClient()
	actual, err := Get(client, "1234asdf").Extract()
	if err != nil {
		t.Fatalf("Unexpected Get error: %v", err)
	}

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestUpdateServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleServerUpdateSuccessfully(t)

	client := client.ServiceClient()
	actual, err := Update(client, "1234asdf", UpdateOpts{Name: "new-name"}).Extract()
	if err != nil {
		t.Fatalf("Unexpected Update error: %v", err)
	}

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestChangeServerAdminPassword(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleAdminPasswordChangeSuccessfully(t)

	res := ChangeAdminPassword(client.ServiceClient(), "1234asdf", "new-password")
	th.AssertNoErr(t, res.Err)
}

func TestRebootServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleRebootSuccessfully(t)

	res := Reboot(client.ServiceClient(), "1234asdf", SoftReboot)
	th.AssertNoErr(t, res.Err)
}

func TestRebuildServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleRebuildSuccessfully(t, SingleServerBody)

	opts := RebuildOpts{
		Name:       "new-name",
		AdminPass:  "swordfish",
		ImageID:    "http://104.130.131.164:8774/fcad67a6189847c4aecfa3c81a05783b/images/f90f6034-2570-4974-8351-6b49732ef2eb",
		AccessIPv4: "1.2.3.4",
	}

	actual, err := Rebuild(client.ServiceClient(), "1234asdf", opts).Extract()
	th.AssertNoErr(t, err)

	th.CheckDeepEquals(t, ServerDerp, *actual)
}

func TestResizeServer(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "resize": { "flavorRef": "2" } }`)

		w.WriteHeader(http.StatusAccepted)
	})

	res := Resize(client.ServiceClient(), "1234asdf", ResizeOpts{FlavorRef: "2"})
	th.AssertNoErr(t, res.Err)
}

func TestConfirmResize(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "confirmResize": null }`)

		w.WriteHeader(http.StatusNoContent)
	})

	res := ConfirmResize(client.ServiceClient(), "1234asdf")
	th.AssertNoErr(t, res.Err)
}

func TestRevertResize(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	th.Mux.HandleFunc("/servers/1234asdf/action", func(w http.ResponseWriter, r *http.Request) {
		th.TestMethod(t, r, "POST")
		th.TestHeader(t, r, "X-Auth-Token", client.TokenID)
		th.TestJSONRequest(t, r, `{ "revertResize": null }`)

		w.WriteHeader(http.StatusAccepted)
	})

	res := RevertResize(client.ServiceClient(), "1234asdf")
	th.AssertNoErr(t, res.Err)
}

func TestRescue(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleServerRescueSuccessfully(t)

	res := Rescue(client.ServiceClient(), "1234asdf", RescueOpts{
		AdminPass: "1234567890",
	})
	th.AssertNoErr(t, res.Err)
	adminPass, _ := res.Extract()
	th.AssertEquals(t, "1234567890", adminPass)
}

func TestGetMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumGetSuccessfully(t)

	expected := map[string]string{"foo": "bar"}
	actual, err := Metadatum(client.ServiceClient(), "1234asdf", "foo").Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestCreateMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumCreateSuccessfully(t)

	expected := map[string]string{"foo": "bar"}
	actual, err := CreateMetadatum(client.ServiceClient(), "1234asdf", MetadatumOpts{"foo": "bar"}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestDeleteMetadatum(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadatumDeleteSuccessfully(t)

	err := DeleteMetadatum(client.ServiceClient(), "1234asdf", "foo").ExtractErr()
	th.AssertNoErr(t, err)
}

func TestGetMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataGetSuccessfully(t)

	expected := map[string]string{"foo": "bar", "this": "that"}
	actual, err := Metadata(client.ServiceClient(), "1234asdf").Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestResetMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataResetSuccessfully(t)

	expected := map[string]string{"foo": "bar", "this": "that"}
	actual, err := ResetMetadata(client.ServiceClient(), "1234asdf", MetadataOpts{
		"foo":  "bar",
		"this": "that",
	}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestUpdateMetadata(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()

	HandleMetadataUpdateSuccessfully(t)

	expected := map[string]string{"foo": "baz", "this": "those"}
	actual, err := UpdateMetadata(client.ServiceClient(), "1234asdf", MetadataOpts{
		"foo":  "baz",
		"this": "those",
	}).Extract()
	th.AssertNoErr(t, err)
	th.AssertDeepEquals(t, expected, actual)
}

func TestListAddresses(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleAddressListSuccessfully(t)

	expected := ListAddressesExpected
	pages := 0
	err := ListAddresses(client.ServiceClient(), "asdfasdfasdf").EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractAddresses(page)
		th.AssertNoErr(t, err)

		if len(actual) != 2 {
			t.Fatalf("Expected 2 networks, got %d", len(actual))
		}
		th.CheckDeepEquals(t, expected, actual)

		return true, nil
	})
	th.AssertNoErr(t, err)
	th.CheckEquals(t, 1, pages)
}

func TestListAddressesByNetwork(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleNetworkAddressListSuccessfully(t)

	expected := ListNetworkAddressesExpected
	pages := 0
	err := ListAddressesByNetwork(client.ServiceClient(), "asdfasdfasdf", "public").EachPage(func(page pagination.Page) (bool, error) {
		pages++

		actual, err := ExtractNetworkAddresses(page)
		th.AssertNoErr(t, err)

		if len(actual) != 2 {
			t.Fatalf("Expected 2 addresses, got %d", len(actual))
		}
		th.CheckDeepEquals(t, expected, actual)

		return true, nil
	})
	th.AssertNoErr(t, err)
	th.CheckEquals(t, 1, pages)
}

func TestCreateServerImage(t *testing.T) {
	th.SetupHTTP()
	defer th.TeardownHTTP()
	HandleCreateServerImageSuccessfully(t)

	_, err := CreateImage(client.ServiceClient(), "serverimage", CreateImageOpts{Name: "test"}).ExtractImageID()
	th.AssertNoErr(t, err)
}

func TestMarshalPersonality(t *testing.T) {
	name := "/etc/test"
	contents := []byte("asdfasdf")

	personality := Personality{
		&File{
			Path:     name,
			Contents: contents,
		},
	}

	data, err := json.Marshal(personality)
	if err != nil {
		t.Fatal(err)
	}

	var actual []map[string]string
	err = json.Unmarshal(data, &actual)
	if err != nil {
		t.Fatal(err)
	}

	if len(actual) != 1 {
		t.Fatal("expected personality length 1")
	}

	if actual[0]["path"] != name {
		t.Fatal("file path incorrect")
	}

	if actual[0]["contents"] != base64.StdEncoding.EncodeToString(contents) {
		t.Fatal("file contents incorrect")
	}
}
<|endoftext|>


<commit_before>// Copyright 2011 Miek Gieben. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package dns

// Holds a bunch of helper functions for dealing with labels.

// SplitDomainName splits a name string into it's labels.
// www.miek.nl. returns []string{"www", "miek", "nl"}
// The root label (.) returns nil.
func SplitDomainName(s string) (labels []string) {
	fqdnEnd := 0 // offset of the final '.' or the length of the name
	idx := Split(s)
	begin := 0

	if s[len(s)-1] == '.' {
		fqdnEnd = len(s) - 1
	} else {
		fqdnEnd = len(s)
	}

	switch len(idx) {
	case 0:
		return nil
	case 1:
		// no-op
	default:
		end := 0
		for i := 1; i < len(idx); i++ {
			end = idx[i]
			labels = append(labels, s[begin:end-1])
			begin = end
		}
	}

	labels = append(labels, s[begin:fqdnEnd])
	return labels
}

// CompareDomainName compares the names s1 and s2 and
// returns how many labels they have in common starting from the *right*.
// The comparison stops at the first inequality. The names are not downcased
// before the comparison.
//
// www.miek.nl. and miek.nl. have two labels in common: miek and nl
// www.miek.nl. and www.bla.nl. have one label in common: nl
func CompareDomainName(s1, s2 string) (n int) {
	s1 = Fqdn(s1)
	s2 = Fqdn(s2)
	l1 := Split(s1)
	l2 := Split(s2)

	// the first check: root label
	if l1 == nil || l2 == nil {
		return
	}

	j1 := len(l1) - 1 // end
	i1 := len(l1) - 2 // start
	j2 := len(l2) - 1
	i2 := len(l2) - 2
	// the second check can be done here: last/only label
	// before we fall through into the for-loop below
	if s1[l1[j1]:] == s2[l2[j2]:] {
		n++
	} else {
		return
	}
	for {
		if i1 < 0 || i2 < 0 {
			break
		}
		if s1[l1[i1]:l1[j1]] == s2[l2[i2]:l2[j2]] {
			n++
		} else {
			break
		}
		j1--
		i1--
		j2--
		i2--
	}
	return
}

// SplitLabels splits a domainname string into its labels.
// www.miek.nl. returns []string{"www", "miek", "nl"}
// The root label (.) returns nil.
func SplitLabels(s string) []string {
	println("SplitLabels is to be removed in future versions, for the better named SplitDomainName")
	return SplitDomainName(s)
}

// CompareLabels compares the names s1 and s2 and
// returns how many labels they have in common starting from the right.
// The comparison stops at the first inequality. The labels are not lower cased
// before the comparison, the caller should take care of this.
//
// www.miek.nl. and miek.nl. have two labels in common: miek and nl
// www.miek.nl. and www.bla.nl. have one label in common: nl
func CompareLabels(s1, s2 string) (n int) {
	println("CompareLabels is to be removed in future versions, for better named CompareDomainName")
	return CompareDomainName(s1, s2)
}

// CountLabel counts the the number of labels in the string s.
func CountLabel(s string) (labels int) {
	if s == "." {
		return
	}
	s = Fqdn(s) // TODO(miek): annoyed I need this
	off := 0
	end := false
	for {
		off, end = NextLabel(s, off)
		labels++
		if end {
			return
		}
	}
}

// LenLabels returns the number of labels in the string s.
func LenLabels(s string) int {
	println("LenLabels is to be removed in future versions, for the better named CountLabel")
	return CountLabel(s)
}

// Split splits a name s into its label indexes.
// www.miek.nl. returns []int{0, 4, 9}. The root name (.) returns nil.
func Split(s string) []int {
	if s == "." {
		return nil
	}
	s = Fqdn(s)     // Grrr!
	idx := []int{0} // TODO(miek): could allocate more (10) and then extend when needed
	off := 0
	end := false

	for {
		off, end = NextLabel(s, off)
		if end {
			return idx
		}
		idx = append(idx, off)
	}
}

// NextLabel returns the index of the start of the next label in the
// string s. The bool end is true when the end of the string has been
// reached.
func NextLabel(s string, offset int) (i int, end bool) {
	quote := false
	for i = offset; i < len(s)-1; i++ {
		switch s[i] {
		case '\\':
			quote = !quote
		default:
			quote = false
		case '.':
			if quote {
				quote = !quote
				continue
			}
			return i + 1, false
		}
	}
	return i + 1, true
}
<commit_msg>Add panics to make older Go versions happy<commit_after>// Copyright 2011 Miek Gieben. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package dns

// Holds a bunch of helper functions for dealing with labels.

// SplitDomainName splits a name string into it's labels.
// www.miek.nl. returns []string{"www", "miek", "nl"}
// The root label (.) returns nil.
func SplitDomainName(s string) (labels []string) {
	fqdnEnd := 0 // offset of the final '.' or the length of the name
	idx := Split(s)
	begin := 0

	if s[len(s)-1] == '.' {
		fqdnEnd = len(s) - 1
	} else {
		fqdnEnd = len(s)
	}

	switch len(idx) {
	case 0:
		return nil
	case 1:
		// no-op
	default:
		end := 0
		for i := 1; i < len(idx); i++ {
			end = idx[i]
			labels = append(labels, s[begin:end-1])
			begin = end
		}
	}

	labels = append(labels, s[begin:fqdnEnd])
	return labels
}

// CompareDomainName compares the names s1 and s2 and
// returns how many labels they have in common starting from the *right*.
// The comparison stops at the first inequality. The names are not downcased
// before the comparison.
//
// www.miek.nl. and miek.nl. have two labels in common: miek and nl
// www.miek.nl. and www.bla.nl. have one label in common: nl
func CompareDomainName(s1, s2 string) (n int) {
	s1 = Fqdn(s1)
	s2 = Fqdn(s2)
	l1 := Split(s1)
	l2 := Split(s2)

	// the first check: root label
	if l1 == nil || l2 == nil {
		return
	}

	j1 := len(l1) - 1 // end
	i1 := len(l1) - 2 // start
	j2 := len(l2) - 1
	i2 := len(l2) - 2
	// the second check can be done here: last/only label
	// before we fall through into the for-loop below
	if s1[l1[j1]:] == s2[l2[j2]:] {
		n++
	} else {
		return
	}
	for {
		if i1 < 0 || i2 < 0 {
			break
		}
		if s1[l1[i1]:l1[j1]] == s2[l2[i2]:l2[j2]] {
			n++
		} else {
			break
		}
		j1--
		i1--
		j2--
		i2--
	}
	return
}

// SplitLabels splits a domainname string into its labels.
// www.miek.nl. returns []string{"www", "miek", "nl"}
// The root label (.) returns nil.
func SplitLabels(s string) []string {
	println("SplitLabels is to be removed in future versions, for the better named SplitDomainName")
	return SplitDomainName(s)
}

// CompareLabels compares the names s1 and s2 and
// returns how many labels they have in common starting from the right.
// The comparison stops at the first inequality. The labels are not lower cased
// before the comparison, the caller should take care of this.
//
// www.miek.nl. and miek.nl. have two labels in common: miek and nl
// www.miek.nl. and www.bla.nl. have one label in common: nl
func CompareLabels(s1, s2 string) (n int) {
	println("CompareLabels is to be removed in future versions, for better named CompareDomainName")
	return CompareDomainName(s1, s2)
}

// CountLabel counts the the number of labels in the string s.
func CountLabel(s string) (labels int) {
	if s == "." {
		return
	}
	s = Fqdn(s) // TODO(miek): annoyed I need this
	off := 0
	end := false
	for {
		off, end = NextLabel(s, off)
		labels++
		if end {
			return
		}
	}
	panic("dns: not reached")
}

// LenLabels returns the number of labels in the string s.
func LenLabels(s string) int {
	println("LenLabels is to be removed in future versions, for the better named CountLabel")
	return CountLabel(s)
}

// Split splits a name s into its label indexes.
// www.miek.nl. returns []int{0, 4, 9}. The root name (.) returns nil.
func Split(s string) []int {
	if s == "." {
		return nil
	}
	s = Fqdn(s)     // Grrr!
	idx := []int{0} // TODO(miek): could allocate more (10) and then extend when needed
	off := 0
	end := false

	for {
		off, end = NextLabel(s, off)
		if end {
			return idx
		}
		idx = append(idx, off)
	}
	panic("dns: not reached")
}

// NextLabel returns the index of the start of the next label in the
// string s. The bool end is true when the end of the string has been
// reached.
func NextLabel(s string, offset int) (i int, end bool) {
	quote := false
	for i = offset; i < len(s)-1; i++ {
		switch s[i] {
		case '\\':
			quote = !quote
		default:
			quote = false
		case '.':
			if quote {
				quote = !quote
				continue
			}
			return i + 1, false
		}
	}
	return i + 1, true
}
<|endoftext|>


<commit_before><commit_msg>Will this fix it?<commit_after><|endoftext|>


<commit_before>// Copyright 2015 syzkaller project authors. All rights reserved.
// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file.

// execprog executes a single program or a set of programs
// and optinally prints information about execution.
package main

import (
	"bufio"
	"bytes"
	"encoding/binary"
	"flag"
	"fmt"
	"io/ioutil"
	"log"
	"os"
	"sync"
	"time"

	"github.com/google/syzkaller/cover"
	"github.com/google/syzkaller/ipc"
	"github.com/google/syzkaller/prog"
)

var (
	flagExecutor  = flag.String("executor", "", "path to executor binary")
	flagThreaded  = flag.Bool("threaded", true, "use threaded mode in executor")
	flagCollide   = flag.Bool("collide", true, "collide syscalls to provoke data races")
	flagDebug     = flag.Bool("debug", false, "debug output from executor")
	flagStrace    = flag.Bool("strace", false, "run executor under strace")
	flagCover     = flag.Bool("cover", true, "collect coverage")
	flagCoverFile = flag.String("coverfile", "", "write coverage to the file")
	flagNobody    = flag.Bool("nobody", true, "impersonate into nobody")
	flagDedup     = flag.Bool("dedup", false, "deduplicate coverage in executor")
	flagLoop      = flag.Bool("loop", false, "execute programs in a loop")
	flagProcs     = flag.Int("procs", 1, "number of parallel processes to execute programs")
	flagNoPgid    = flag.Bool("nopgid", false, "don't use setpgid syscall")
	flagTimeout   = flag.Duration("timeout", 10*time.Second, "execution timeout")
)

func main() {
	flag.Parse()
	if len(flag.Args()) == 0 {
		fmt.Fprintf(os.Stderr, "usage: execprog [flags] file-with-programs*\n")
		flag.PrintDefaults()
		os.Exit(1)
	}

	var progs []*prog.Prog
	for _, fn := range flag.Args() {
		progs = append(progs, parseFile(fn)...)
	}
	log.Printf("parsed %v programs", len(progs))
	if len(progs) == 0 {
		return
	}

	var flags uint64
	if *flagThreaded {
		flags |= ipc.FlagThreaded
	}
	if *flagCollide {
		flags |= ipc.FlagCollide
	}
	if *flagDebug {
		flags |= ipc.FlagDebug
	}
	if *flagStrace {
		flags |= ipc.FlagStrace
	}
	if *flagCover || *flagCoverFile != "" {
		flags |= ipc.FlagCover
	}
	if *flagDedup {
		flags |= ipc.FlagDedupCover
	}
	if *flagNobody {
		flags |= ipc.FlagDropPrivs
	}
	if *flagNoPgid {
		flags |= ipc.FlagNoSetpgid
	}

	var wg sync.WaitGroup
	wg.Add(*flagProcs)
	var posMu sync.Mutex
	var pos int
	var lastPrint time.Time
	for p := 0; p < *flagProcs; p++ {
		go func() {
			env, err := ipc.MakeEnv(*flagExecutor, *flagTimeout, flags)
			if err != nil {
				log.Fatalf("failed to create ipc env: %v", err)
			}
			for {
				posMu.Lock()
				idx := pos
				pos++
				if idx%len(progs) == 0 && time.Since(lastPrint) > 5*time.Second {
					log.Printf("executed %v programs\n", idx)
					lastPrint = time.Now()
				}
				posMu.Unlock()
				if !*flagLoop && idx >= len(progs) {
					env.Close()
					wg.Done()
					return
				}
				p := progs[idx%len(progs)]
				output, strace, cov, _, failed, hanged, err := env.Exec(p)
				if *flagDebug || err != nil {
					fmt.Printf("result: failed=%v hanged=%v err=%v\n\n%s", failed, hanged, err, output)
				}
				if *flagStrace {
					fmt.Printf("strace output:\n%s", strace)
				}
				if *flagCoverFile != "" {
					// Coverage is dumped in sanitizer format.
					// github.com/google/sanitizers/tools/sancov command can be used to dump PCs,
					// then they can be piped via addr2line to symbolize.
					for i, c := range cov {
						fmt.Printf("call #%v: coverage %v\n", i, len(c))
						if len(c) == 0 {
							continue
						}
						buf := new(bytes.Buffer)
						binary.Write(buf, binary.LittleEndian, uint64(0xC0BFFFFFFFFFFF64))
						for _, pc := range c {
							binary.Write(buf, binary.LittleEndian, cover.RestorePC(pc))
						}
						err := ioutil.WriteFile(fmt.Sprintf("%v.%v", *flagCoverFile, i), buf.Bytes(), 0660)
						if err != nil {
							log.Fatalf("failed to write coverage file: %v", err)
						}
					}
				}
			}
		}()
	}
	wg.Wait()
}

func parseFile(fn string) []*prog.Prog {
	logf, err := os.Open(fn)
	if err != nil {
		log.Fatalf("failed to open log file: %v", err)
	}
	log.Printf("parsing log %v", fn)
	s := bufio.NewScanner(logf)
	var cur []byte
	var last *prog.Prog
	var progs []*prog.Prog
	for s.Scan() {
		ln := s.Text()
		tmp := append(cur, ln...)
		tmp = append(tmp, '\n')
		p, err := prog.Deserialize(tmp)
		if err == nil {
			cur = tmp
			last = p
			continue
		}
		if last != nil {
			progs = append(progs, last)
			last = nil
			cur = cur[:0]
		}
	}
	if last != nil {
		progs = append(progs, last)
	}
	return progs
}
<commit_msg>execprog: replace loop flag with repeat<commit_after>// Copyright 2015 syzkaller project authors. All rights reserved.
// Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file.

// execprog executes a single program or a set of programs
// and optinally prints information about execution.
package main

import (
	"bufio"
	"bytes"
	"encoding/binary"
	"flag"
	"fmt"
	"io/ioutil"
	"log"
	"os"
	"sync"
	"time"

	"github.com/google/syzkaller/cover"
	"github.com/google/syzkaller/ipc"
	"github.com/google/syzkaller/prog"
)

var (
	flagExecutor  = flag.String("executor", "", "path to executor binary")
	flagThreaded  = flag.Bool("threaded", true, "use threaded mode in executor")
	flagCollide   = flag.Bool("collide", true, "collide syscalls to provoke data races")
	flagDebug     = flag.Bool("debug", false, "debug output from executor")
	flagStrace    = flag.Bool("strace", false, "run executor under strace")
	flagCover     = flag.Bool("cover", true, "collect coverage")
	flagCoverFile = flag.String("coverfile", "", "write coverage to the file")
	flagNobody    = flag.Bool("nobody", true, "impersonate into nobody")
	flagDedup     = flag.Bool("dedup", false, "deduplicate coverage in executor")
	flagRepeat    = flag.Int("repeat", 1, "repeat execution that many times (0 for infinite loop)")
	flagProcs     = flag.Int("procs", 1, "number of parallel processes to execute programs")
	flagNoPgid    = flag.Bool("nopgid", false, "don't use setpgid syscall")
	flagTimeout   = flag.Duration("timeout", 10*time.Second, "execution timeout")
)

func main() {
	flag.Parse()
	if len(flag.Args()) == 0 {
		fmt.Fprintf(os.Stderr, "usage: execprog [flags] file-with-programs*\n")
		flag.PrintDefaults()
		os.Exit(1)
	}

	var progs []*prog.Prog
	for _, fn := range flag.Args() {
		progs = append(progs, parseFile(fn)...)
	}
	log.Printf("parsed %v programs", len(progs))
	if len(progs) == 0 {
		return
	}

	var flags uint64
	if *flagThreaded {
		flags |= ipc.FlagThreaded
	}
	if *flagCollide {
		flags |= ipc.FlagCollide
	}
	if *flagDebug {
		flags |= ipc.FlagDebug
	}
	if *flagStrace {
		flags |= ipc.FlagStrace
	}
	if *flagCover || *flagCoverFile != "" {
		flags |= ipc.FlagCover
	}
	if *flagDedup {
		flags |= ipc.FlagDedupCover
	}
	if *flagNobody {
		flags |= ipc.FlagDropPrivs
	}
	if *flagNoPgid {
		flags |= ipc.FlagNoSetpgid
	}

	var wg sync.WaitGroup
	wg.Add(*flagProcs)
	var posMu sync.Mutex
	var pos int
	var lastPrint time.Time
	for p := 0; p < *flagProcs; p++ {
		go func() {
			env, err := ipc.MakeEnv(*flagExecutor, *flagTimeout, flags)
			if err != nil {
				log.Fatalf("failed to create ipc env: %v", err)
			}
			for {
				posMu.Lock()
				idx := pos
				pos++
				if idx%len(progs) == 0 && time.Since(lastPrint) > 5*time.Second {
					log.Printf("executed %v programs\n", idx)
					lastPrint = time.Now()
				}
				posMu.Unlock()
				if *flagRepeat > 0 && idx >= len(progs)**flagRepeat {
					env.Close()
					wg.Done()
					return
				}
				p := progs[idx%len(progs)]
				output, strace, cov, _, failed, hanged, err := env.Exec(p)
				if *flagDebug || err != nil {
					fmt.Printf("result: failed=%v hanged=%v err=%v\n\n%s", failed, hanged, err, output)
				}
				if *flagStrace {
					fmt.Printf("strace output:\n%s", strace)
				}
				if *flagCoverFile != "" {
					// Coverage is dumped in sanitizer format.
					// github.com/google/sanitizers/tools/sancov command can be used to dump PCs,
					// then they can be piped via addr2line to symbolize.
					for i, c := range cov {
						fmt.Printf("call #%v: coverage %v\n", i, len(c))
						if len(c) == 0 {
							continue
						}
						buf := new(bytes.Buffer)
						binary.Write(buf, binary.LittleEndian, uint64(0xC0BFFFFFFFFFFF64))
						for _, pc := range c {
							binary.Write(buf, binary.LittleEndian, cover.RestorePC(pc))
						}
						err := ioutil.WriteFile(fmt.Sprintf("%v.%v", *flagCoverFile, i), buf.Bytes(), 0660)
						if err != nil {
							log.Fatalf("failed to write coverage file: %v", err)
						}
					}
				}
			}
		}()
	}
	wg.Wait()
}

func parseFile(fn string) []*prog.Prog {
	logf, err := os.Open(fn)
	if err != nil {
		log.Fatalf("failed to open log file: %v", err)
	}
	log.Printf("parsing log %v", fn)
	s := bufio.NewScanner(logf)
	var cur []byte
	var last *prog.Prog
	var progs []*prog.Prog
	for s.Scan() {
		ln := s.Text()
		tmp := append(cur, ln...)
		tmp = append(tmp, '\n')
		p, err := prog.Deserialize(tmp)
		if err == nil {
			cur = tmp
			last = p
			continue
		}
		if last != nil {
			progs = append(progs, last)
			last = nil
			cur = cur[:0]
		}
	}
	if last != nil {
		progs = append(progs, last)
	}
	return progs
}
<|endoftext|>


<commit_before>// +build !ignore_autogenerated

/*
Copyright The Kubernetes 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.
*/

// Code generated by deepcopy-gen. DO NOT EDIT.

package v1alpha1

import (
	runtime "k8s.io/apimachinery/pkg/runtime"
)

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *Foo) DeepCopyInto(out *Foo) {
	*out = *in
	out.TypeMeta = in.TypeMeta
	in.ObjectMeta.DeepCopyInto(&out.ObjectMeta)
	in.Spec.DeepCopyInto(&out.Spec)
	out.Status = in.Status
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Foo.
func (in *Foo) DeepCopy() *Foo {
	if in == nil {
		return nil
	}
	out := new(Foo)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
func (in *Foo) DeepCopyObject() runtime.Object {
	if c := in.DeepCopy(); c != nil {
		return c
	}
	return nil
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooList) DeepCopyInto(out *FooList) {
	*out = *in
	out.TypeMeta = in.TypeMeta
	out.ListMeta = in.ListMeta
	if in.Items != nil {
		in, out := &in.Items, &out.Items
		*out = make([]Foo, len(*in))
		for i := range *in {
			(*in)[i].DeepCopyInto(&(*out)[i])
		}
	}
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooList.
func (in *FooList) DeepCopy() *FooList {
	if in == nil {
		return nil
	}
	out := new(FooList)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
func (in *FooList) DeepCopyObject() runtime.Object {
	if c := in.DeepCopy(); c != nil {
		return c
	}
	return nil
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooSpec) DeepCopyInto(out *FooSpec) {
	*out = *in
	if in.Replicas != nil {
		in, out := &in.Replicas, &out.Replicas
		*out = new(int32)
		**out = **in
	}
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooSpec.
func (in *FooSpec) DeepCopy() *FooSpec {
	if in == nil {
		return nil
	}
	out := new(FooSpec)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooStatus) DeepCopyInto(out *FooStatus) {
	*out = *in
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooStatus.
func (in *FooStatus) DeepCopy() *FooStatus {
	if in == nil {
		return nil
	}
	out := new(FooStatus)
	in.DeepCopyInto(out)
	return out
}
<commit_msg>generated<commit_after>// +build !ignore_autogenerated

/*
Copyright The Kubernetes 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.
*/

// Code generated by deepcopy-gen. DO NOT EDIT.

package v1alpha1

import (
	runtime "k8s.io/apimachinery/pkg/runtime"
)

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *Foo) DeepCopyInto(out *Foo) {
	*out = *in
	out.TypeMeta = in.TypeMeta
	in.ObjectMeta.DeepCopyInto(&out.ObjectMeta)
	in.Spec.DeepCopyInto(&out.Spec)
	out.Status = in.Status
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Foo.
func (in *Foo) DeepCopy() *Foo {
	if in == nil {
		return nil
	}
	out := new(Foo)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
func (in *Foo) DeepCopyObject() runtime.Object {
	if c := in.DeepCopy(); c != nil {
		return c
	}
	return nil
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooList) DeepCopyInto(out *FooList) {
	*out = *in
	out.TypeMeta = in.TypeMeta
	in.ListMeta.DeepCopyInto(&out.ListMeta)
	if in.Items != nil {
		in, out := &in.Items, &out.Items
		*out = make([]Foo, len(*in))
		for i := range *in {
			(*in)[i].DeepCopyInto(&(*out)[i])
		}
	}
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooList.
func (in *FooList) DeepCopy() *FooList {
	if in == nil {
		return nil
	}
	out := new(FooList)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
func (in *FooList) DeepCopyObject() runtime.Object {
	if c := in.DeepCopy(); c != nil {
		return c
	}
	return nil
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooSpec) DeepCopyInto(out *FooSpec) {
	*out = *in
	if in.Replicas != nil {
		in, out := &in.Replicas, &out.Replicas
		*out = new(int32)
		**out = **in
	}
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooSpec.
func (in *FooSpec) DeepCopy() *FooSpec {
	if in == nil {
		return nil
	}
	out := new(FooSpec)
	in.DeepCopyInto(out)
	return out
}

// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *FooStatus) DeepCopyInto(out *FooStatus) {
	*out = *in
	return
}

// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new FooStatus.
func (in *FooStatus) DeepCopy() *FooStatus {
	if in == nil {
		return nil
	}
	out := new(FooStatus)
	in.DeepCopyInto(out)
	return out
}
<|endoftext|>